diff --git a/exportfs-exit-with-error-code-if-there-was-any-error.patch b/exportfs-exit-with-error-code-if-there-was-any-error.patch new file mode 100644 index 0000000..d479991 --- /dev/null +++ b/exportfs-exit-with-error-code-if-there-was-any-error.patch @@ -0,0 +1,121 @@ +From e10ddcb9d913f7938fc37c72568eea4e8287ade4 Mon Sep 17 00:00:00 2001 +From: Neil Brown +Date: Mon, 21 Oct 2013 17:40:55 +1100 +Subject: [PATCH] exportfs: exit with error code if there was any error. +Reference: bnc#846064 + +exportfs currently exits with a non-zero error for some errors, +but not for others. + +It does this by having various support routines set the global +variable "export_errno". + +Change this to have 'xlog' set export_errno if an ERROR is +reported. That way all errors will be caught. + +Note that the exit error code is changed from 22 (EINVAL) +to the more traditional '1'. + +Signed-off-by: NeilBrown +--- + support/include/exportfs.h | 3 --- + support/include/xlog.h | 1 + + support/nfs/exports.c | 6 ------ + support/nfs/xlog.c | 4 ++++ + utils/exportfs/exportfs.c | 2 -- + 5 files changed, 5 insertions(+), 11 deletions(-) + +--- nfs-utils-1.2.8.orig/support/include/exportfs.h ++++ nfs-utils-1.2.8/support/include/exportfs.h +@@ -179,7 +179,4 @@ struct export_features { + struct export_features *get_export_features(void); + void fix_pseudoflavor_flags(struct exportent *ep); + +-/* Record export error. */ +-extern int export_errno; +- + #endif /* EXPORTFS_H */ +--- nfs-utils-1.2.8.orig/support/include/xlog.h ++++ nfs-utils-1.2.8/support/include/xlog.h +@@ -35,6 +35,7 @@ struct xlog_debugfac { + int df_fac; + }; + ++extern int export_errno; + void xlog_open(char *progname); + void xlog_stderr(int on); + void xlog_syslog(int on); +--- nfs-utils-1.2.8.orig/support/nfs/exports.c ++++ nfs-utils-1.2.8/support/nfs/exports.c +@@ -47,8 +47,6 @@ struct flav_info flav_map[] = { + + const int flav_map_size = sizeof(flav_map)/sizeof(flav_map[0]); + +-int export_errno; +- + static char *efname = NULL; + static XFILE *efp = NULL; + static int first; +@@ -132,7 +130,6 @@ getexportent(int fromkernel, int fromexp + } + if (ok < 0) { + xlog(L_ERROR, "expected client(options...)"); +- export_errno = EINVAL; + return NULL; + } + first = 0; +@@ -152,7 +149,6 @@ getexportent(int fromkernel, int fromexp + ok = getexport(exp, sizeof(exp)); + if (ok < 0) { + xlog(L_ERROR, "expected client(options...)"); +- export_errno = EINVAL; + return NULL; + } + } +@@ -172,7 +168,6 @@ getexportent(int fromkernel, int fromexp + *opt++ = '\0'; + if (!(sp = strchr(opt, ')')) || sp[1] != '\0') { + syntaxerr("bad option list"); +- export_errno = EINVAL; + return NULL; + } + *sp = '\0'; +@@ -567,7 +562,6 @@ parseopts(char *cp, struct exportent *ep + flname, flline, opt); + bad_option: + free(opt); +- export_errno = EINVAL; + return -1; + } + } else if (strncmp(opt, "anongid=", 8) == 0) { +--- nfs-utils-1.2.8.orig/support/nfs/xlog.c ++++ nfs-utils-1.2.8/support/nfs/xlog.c +@@ -38,6 +38,8 @@ static int logmask = 0; /* What will b + static char log_name[256]; /* name of this program */ + static int log_pid = -1; /* PID of this program */ + ++int export_errno = 0; ++ + static void xlog_toggle(int sig); + static struct xlog_debugfac debugnames[] = { + { "general", D_GENERAL, }, +@@ -189,6 +191,8 @@ void + xlog(int kind, const char* fmt, ...) + { + va_list args; ++ if (kind & (L_ERROR|D_GENERAL)) ++ export_errno = 1; + + va_start(args, fmt); + xlog_backend(kind, fmt, args); +--- nfs-utils-1.2.8.orig/utils/exportfs/exportfs.c ++++ nfs-utils-1.2.8/utils/exportfs/exportfs.c +@@ -103,8 +103,6 @@ main(int argc, char **argv) + xlog_stderr(1); + xlog_syslog(0); + +- export_errno = 0; +- + while ((c = getopt(argc, argv, "afhio:ruv")) != EOF) { + switch(c) { + case 'a': diff --git a/exportfs-report-failure-if-asked-to-unexport-somethi.patch b/exportfs-report-failure-if-asked-to-unexport-somethi.patch new file mode 100644 index 0000000..0b6b499 --- /dev/null +++ b/exportfs-report-failure-if-asked-to-unexport-somethi.patch @@ -0,0 +1,40 @@ +From 609bce0c7efde1875d1477d96fe1f359b6403005 Mon Sep 17 00:00:00 2001 +From: Neil Brown +Date: Mon, 28 Oct 2013 14:40:15 +1100 +Subject: [PATCH] exportfs: report failure if asked to unexport something not + exported. +Reference: bnc#846064 + +Currently if exportfs is asked to unexport something that is not +exported it silently succeeds. This is not ideal, particularly for +scripting situations. + +So report an error unless the unexport was successful. + +Reported-by: Tony Asleson +Signed-off-by: NeilBrown +--- + utils/exportfs/exportfs.c | 4 ++++ + 1 file changed, 4 insertions(+) + +--- nfs-utils-1.2.8.orig/utils/exportfs/exportfs.c ++++ nfs-utils-1.2.8/utils/exportfs/exportfs.c +@@ -345,6 +345,7 @@ unexportfs(char *arg, int verbose) + char *path; + char *hname = arg; + int htype; ++ int success = 0; + + if ((path = strchr(arg, ':')) != NULL) + *path++ = '\0'; +@@ -391,7 +392,10 @@ unexportfs(char *arg, int verbose) + #endif + exp->m_xtabent = 0; + exp->m_mayexport = 0; ++ success = 1; + } ++ if (!success) ++ xlog(L_ERROR, "Could not find %s to unexport.\n", arg); + + freeaddrinfo(ai); + } diff --git a/nfs-utils.changes b/nfs-utils.changes index b94c95b..b959f73 100644 --- a/nfs-utils.changes +++ b/nfs-utils.changes @@ -1,3 +1,17 @@ +------------------------------------------------------------------- +Wed Nov 6 02:06:45 UTC 2013 - nfbrown@suse.com + +- nfs-utils.spec: add various systemd macros to make + sure init scripts are registered properly + bnc#845475 +- nfs.int, nfsserver.init: run gssd on server as well + as on client. This is needed for NFSv4.0 callbacks. + bnc#845269 +- exportfs-exit-with-error-code-if-there-was-any-error.patch +- exportfs-report-failure-if-asked-to-unexport-somethi.patch + Return good error code from exportfs. + bnc#846064 + ------------------------------------------------------------------- Tue Oct 22 04:45:13 UTC 2013 - nfbrown@suse.com diff --git a/nfs-utils.spec b/nfs-utils.spec index 1d9745c..16e9101 100644 --- a/nfs-utils.spec +++ b/nfs-utils.spec @@ -31,6 +31,9 @@ BuildRequires: nfsidmap-devel >= 0.24 BuildRequires: pkgconfig BuildRequires: sqlite3-devel BuildRequires: tcpd-devel +%if 0%{?suse_version} >= 1210 +BuildRequires: systemd +%endif Url: http://kernel.org/pub/linux/utils/nfs-utils/ Summary: Support Utilities for Kernel nfsd License: GPL-2.0+ @@ -39,6 +42,7 @@ Version: 1.2.8 Release: 0 BuildRoot: %{_tmppath}/%{name}-%{version}-build PreReq: %fillup_prereq %insserv_prereq +%{?systemd_requires} BuildRoot: %{_tmppath}/%{name}-%{version}-build Source0: http://kernel.org/pub/linux/utils/nfs-utils/%{version}/nfs-utils-%{version}.tar.bz2 # Download does not work: @@ -73,6 +77,10 @@ Patch6: 0006-gssd-fixed-typo-in-machine-cred-name.patch Patch7: skip-on-ENOENT.patch # PATCH-FIX-UPSTREAM mountd-fix-bug-affecting-exports-of-dirs-with-64bit-.patch nfbrown@suse.de Patch8: mountd-fix-bug-affecting-exports-of-dirs-with-64bit-.patch +# PATCH-FIX-UPSTREAM exportfs-exit-with-error-code-if-there-was-any-error.patch nfbrown@suse.de +Patch9: exportfs-exit-with-error-code-if-there-was-any-error.patch +# PATCH-FIX_UPSTREAM exportfs-report-failure-if-asked-to-unexport-somethi.patch nfbrown@suse.de +Patch10: exportfs-report-failure-if-asked-to-unexport-somethi.patch Suggests: python-base %description @@ -131,6 +139,8 @@ This package contains additional NFS documentation. %patch6 -p1 %patch7 -p1 %patch8 -p1 +%patch9 -p1 +%patch10 -p1 cp %{S:6} . %build @@ -194,6 +204,7 @@ rm -rf $RPM_BUILD_ROOT %pre -n nfs-client useradd -r -c 'NFS statd daemon' \ -s /sbin/nologin -d /var/lib/nfs -g nogroup statd &> /dev/null || : +%service_add_pre nfs %post -n nfs-client chown statd:nogroup /var/lib/nfs @@ -211,20 +222,27 @@ fi %{fillup_and_insserv -n nfs nfs} # %set_permissions /sbin/mount.nfs +%service_add_post nfs %preun -n nfs-client %stop_on_removal nfs +%service_del_preun nfs %postun -n nfs-client %restart_on_update nfs [ -x /sbin/mkinitrd_setup ] && mkinitrd_setup %insserv_cleanup +%service_del_postun nfs %verifyscript -n nfs-client %verify_permissions -e /sbin/mount.nfs +%pre -n nfs-kernel-server +%service_add_pre nfsserver + %preun -n nfs-kernel-server %stop_on_removal nfsserver +%service_del_preun nfsserver %post -n nfs-kernel-server ### migrate from /var/lock/subsys @@ -237,10 +255,12 @@ if [ -f /var/lock/subsys/nfsserver-rpc.idmapd ]; then fi ### %{fillup_and_insserv nfsserver} +%service_add_post nfsserver %postun -n nfs-kernel-server %restart_on_update nfsserver %insserv_cleanup +%service_del_postun nfsserver %files -n nfs-client %defattr(-,root,root) diff --git a/nfs.init b/nfs.init index 85d2314..870fbe6 100644 --- a/nfs.init +++ b/nfs.init @@ -31,6 +31,8 @@ STATD_BIN=/usr/sbin/rpc.statd IDMAPD_CLIENT_STATE=/run/nfs/nfs-rpc.idmapd IDMAPD_SERVER_STATE=/run/nfs/nfsserver-rpc.idmapd +GSSD_CLIENT_STATE=/run/nfs/nfs-rpc.gssd +GSSD_SERVER_STATE=/run/nfs/nfsserver-rpc.gssd if [ -z "$RPC_PIPEFS_DIR" ]; then RPC_PIPEFS_DIR=/var/lib/nfs/rpc_pipefs @@ -163,7 +165,7 @@ do_start_gssd() { /sbin/modprobe rpcsec_gss_$flavor done mount_rpc_pipefs - startproc $GSSD_BIN $ignore_dns $GSSD_OPTIONS + startproc $GSSD_BIN $ignore_dns $GSSD_OPTIONS -p $RPC_PIPEFS_DIR return $? } @@ -175,7 +177,7 @@ do_start_idmapd() { if checkproc $IDMAPD_BIN && test -f $IDMAPD_SERVER_STATE; then killproc -HUP $IDMAPD_BIN else - startproc $IDMAPD_BIN + startproc $IDMAPD_BIN -p $RPC_PIPEFS_DIR return $? fi } @@ -220,6 +222,7 @@ case "$1-$nfs" in rc_status -v rc_exit } + echo $GSSD_BIN > $GSSD_CLIENT_STATE fi # start idmapd @@ -291,9 +294,12 @@ case "$1-$nfs" in umount -alt nfs,nfs4 # stop gssd - if checkproc $GSSD_BIN; then - echo -n " gssd" - killproc $GSSD_BIN + if test ! -f $GSSD_SERVER_STATE ; then + if checkproc $GSSD_BIN; then + echo -n " gssd" + killproc $GSSD_BIN + fi + rm -f $GSSD_CLIENT_STATE fi # stop idmapd @@ -314,7 +320,10 @@ case "$1-$nfs" in fi fi - umount_rpc_pipefs + # umount rpc_pipefs only if not needed by server + if [ ! -f $GSSD_SERVER_STATE -a ! -f $IDMAPD_SERVER_STATE ]; then + umount_rpc_pipefs + fi rc_status -v fi diff --git a/nfsserver.init b/nfsserver.init index 2325866..6b93e7e 100644 --- a/nfsserver.init +++ b/nfsserver.init @@ -52,12 +52,15 @@ rc_reset # XXX: there should be separate init scripts for these really SVCGSSD_BIN=/usr/sbin/rpc.svcgssd +GSSD_BIN=/usr/sbin/rpc.gssd IDMAPD_BIN=/usr/sbin/rpc.idmapd NFSD_BIN=/usr/sbin/rpc.nfsd IDMAPD_CLIENT_STATE=/run/nfs/nfs-rpc.idmapd IDMAPD_SERVER_STATE=/run/nfs/nfsserver-rpc.idmapd NFSD_BIND_MOUNTS=/run/nfs/bind.mounts +GSSD_CLIENT_STATE=/run/nfs/nfs-rpc.gssd +GSSD_SERVER_STATE=/run/nfs/nfsserver-rpc.gssd NEED_SVCGSSD=no NEED_IDMPAPD=no @@ -152,13 +155,26 @@ do_start_svcgssd() { return $? } +do_start_gssd() { + if ! checkproc $GSSD_BIN; then + case $NFS_GSSD_AVOID_DNS in + [Nn]*) ignore_dns=-D ;; + [Yy]*) ignore_dns= ;; + * ) ignore_dns=-D + esac + mount_rpc_pipefs + startproc $GSSD_BIN $ignore_dns $GSSD_OPTIONS -p $RPC_PIPEFS_DIR + return $? + fi +} + do_start_idmapd() { mount_rpc_pipefs if checkproc $IDMAPD_BIN && test -f $IDMAPD_CLIENT_STATE; then killproc -HUP $IDMAPD_BIN else - startproc $IDMAPD_BIN + startproc $IDMAPD_BIN -p $RPC_PIPEFS_DIR return $? fi } @@ -196,13 +212,19 @@ case "$1" in fi nfs4_bind_mounts - # svcgssd; idmapd + # svcgssd; gssd; idmapd if [ "$NEED_SVCGSSD" = yes ]; then echo -n " svcgssd" do_start_svcgssd || { - rc_status -v + rc_status -v rc_exit } + echo -n " gssd" + do_start_gssd || { + rc_status -v + rc_exit + } + echo $GSSD_BIN > $GSSD_SERVER_STATE fi if [ "$NEED_IDMAPD" = yes ]; then echo -n " idmapd" @@ -277,6 +299,15 @@ case "$1" in rc_status -v rc_exit } + # kill only if not needed by client anymore + if [ ! -f $GSSD_CLIENT_STATE ]; then + echo -n " gssd" + killproc $GSSD_BIN || { + rc_status -v + rc_exit + } + fi + rm -f $GSSD_SERVER_STATE fi # idmap if [ "$NEED_IDMAPD" = yes ]; then @@ -287,11 +318,15 @@ case "$1" in fi rm -f $IDMAPD_SERVER_STATE fi + # umount rpc_pipefs only if not needed by client + if [ ! -f $GSSD_CLIENT_STATE -a ! -f $IDMAPD_CLIENT_STATE ] ; then + umount_rpc_pipefs + fi # umount nfsd fs check_for_nfsdfs if [ "$HAVE_NFSDFS" = "yes" -a -f /proc/fs/nfsd/exports ] ; then - umount /proc/fs/nfsd - rc_status + umount /proc/fs/nfsd + rc_status fi nfs4_unbind_mounts # @@ -337,6 +372,9 @@ case "$1" in echo -n " svcgssd" checkproc $SVCGSSD_BIN rc_status -v + echo -n " gssd" + checkproc $GSSD_BIN + rc_status -v fi if [ "$NEED_IDMAPD" = yes ]; then echo -n " idmapd"