From 4897093455a2bf08f3db3a1132cc2f6f5484d77c Mon Sep 17 00:00:00 2001 From: Daniel Baumann Date: Fri, 19 Apr 2024 08:03:02 +0200 Subject: Adding upstream version 1:2.6.4. Signed-off-by: Daniel Baumann --- utils/exportfs/Makefile.am | 18 + utils/exportfs/Makefile.in | 920 ++++++++++++++++++++++++++++++++++++++++++++ utils/exportfs/exportfs.c | 768 ++++++++++++++++++++++++++++++++++++ utils/exportfs/exportfs.man | 337 ++++++++++++++++ utils/exportfs/exports.man | 678 ++++++++++++++++++++++++++++++++ utils/exportfs/nfsd.man | 214 +++++++++++ 6 files changed, 2935 insertions(+) create mode 100644 utils/exportfs/Makefile.am create mode 100644 utils/exportfs/Makefile.in create mode 100644 utils/exportfs/exportfs.c create mode 100644 utils/exportfs/exportfs.man create mode 100644 utils/exportfs/exports.man create mode 100644 utils/exportfs/nfsd.man (limited to 'utils/exportfs') diff --git a/utils/exportfs/Makefile.am b/utils/exportfs/Makefile.am new file mode 100644 index 0000000..7f8ce9f --- /dev/null +++ b/utils/exportfs/Makefile.am @@ -0,0 +1,18 @@ +## Process this file with automake to produce Makefile.in + +man5_MANS = exports.man +man7_MANS = nfsd.man +man8_MANS = exportfs.man + +EXTRA_DIST = $(man5_MANS) $(man7_MANS) $(man8_MANS) +sbin_PROGRAMS = exportfs +exportfs_SOURCES = exportfs.c +exportfs_LDADD = ../../support/export/libexport.a \ + ../../support/nfs/libnfs.la \ + ../../support/misc/libmisc.a \ + ../../support/reexport/libreexport.a \ + $(LIBWRAP) $(LIBNSL) $(LIBPTHREAD) + +exportfs_CPPFLAGS = $(AM_CPPFLAGS) $(CPPFLAGS) -I$(top_srcdir)/support/reexport + +MAINTAINERCLEANFILES = Makefile.in diff --git a/utils/exportfs/Makefile.in b/utils/exportfs/Makefile.in new file mode 100644 index 0000000..3fd8dc0 --- /dev/null +++ b/utils/exportfs/Makefile.in @@ -0,0 +1,920 @@ +# Makefile.in generated by automake 1.16.5 from Makefile.am. +# @configure_input@ + +# Copyright (C) 1994-2021 Free Software Foundation, Inc. + +# This Makefile.in is free software; the Free Software Foundation +# gives unlimited permission to copy and/or distribute it, +# with or without modifications, as long as this notice is preserved. + +# This program is distributed in the hope that it will be useful, +# but WITHOUT ANY WARRANTY, to the extent permitted by law; without +# even the implied warranty of MERCHANTABILITY or FITNESS FOR A +# PARTICULAR PURPOSE. + +@SET_MAKE@ + +VPATH = @srcdir@ +am__is_gnu_make = { \ + if test -z '$(MAKELEVEL)'; then \ + false; \ + elif test -n '$(MAKE_HOST)'; then \ + true; \ + elif test -n '$(MAKE_VERSION)' && test -n '$(CURDIR)'; then \ + true; \ + else \ + false; \ + fi; \ +} +am__make_running_with_option = \ + case $${target_option-} in \ + ?) ;; \ + *) echo "am__make_running_with_option: internal error: invalid" \ + "target option '$${target_option-}' specified" >&2; \ + exit 1;; \ + esac; \ + has_opt=no; \ + sane_makeflags=$$MAKEFLAGS; \ + if $(am__is_gnu_make); then \ + sane_makeflags=$$MFLAGS; \ + else \ + case $$MAKEFLAGS in \ + *\\[\ \ ]*) \ + bs=\\; \ + sane_makeflags=`printf '%s\n' "$$MAKEFLAGS" \ + | sed "s/$$bs$$bs[$$bs $$bs ]*//g"`;; \ + esac; \ + fi; \ + skip_next=no; \ + strip_trailopt () \ + { \ + flg=`printf '%s\n' "$$flg" | sed "s/$$1.*$$//"`; \ + }; \ + for flg in $$sane_makeflags; do \ + test $$skip_next = yes && { skip_next=no; continue; }; \ + case $$flg in \ + *=*|--*) continue;; \ + -*I) strip_trailopt 'I'; skip_next=yes;; \ + -*I?*) strip_trailopt 'I';; \ + -*O) strip_trailopt 'O'; skip_next=yes;; \ + -*O?*) strip_trailopt 'O';; \ + -*l) strip_trailopt 'l'; skip_next=yes;; \ + -*l?*) strip_trailopt 'l';; \ + -[dEDm]) skip_next=yes;; \ + -[JT]) skip_next=yes;; \ + esac; \ + case $$flg in \ + *$$target_option*) has_opt=yes; break;; \ + esac; \ + done; \ + test $$has_opt = yes +am__make_dryrun = (target_option=n; $(am__make_running_with_option)) +am__make_keepgoing = (target_option=k; $(am__make_running_with_option)) +pkgdatadir = $(datadir)/@PACKAGE@ +pkgincludedir = $(includedir)/@PACKAGE@ +pkglibdir = $(libdir)/@PACKAGE@ +pkglibexecdir = $(libexecdir)/@PACKAGE@ +am__cd = CDPATH="$${ZSH_VERSION+.}$(PATH_SEPARATOR)" && cd +install_sh_DATA = $(install_sh) -c -m 644 +install_sh_PROGRAM = $(install_sh) -c +install_sh_SCRIPT = $(install_sh) -c +INSTALL_HEADER = $(INSTALL_DATA) +transform = $(program_transform_name) +NORMAL_INSTALL = : +PRE_INSTALL = : +POST_INSTALL = : +NORMAL_UNINSTALL = : +PRE_UNINSTALL = : +POST_UNINSTALL = : +build_triplet = @build@ +host_triplet = @host@ +sbin_PROGRAMS = exportfs$(EXEEXT) +subdir = utils/exportfs +ACLOCAL_M4 = $(top_srcdir)/aclocal.m4 +am__aclocal_m4_deps = $(top_srcdir)/aclocal/ax_gcc_func_attribute.m4 \ + $(top_srcdir)/aclocal/bsdsignals.m4 \ + $(top_srcdir)/aclocal/getrandom.m4 \ + $(top_srcdir)/aclocal/ipv6.m4 \ + $(top_srcdir)/aclocal/kerberos5.m4 \ + $(top_srcdir)/aclocal/keyutils.m4 \ + $(top_srcdir)/aclocal/libblkid.m4 \ + $(top_srcdir)/aclocal/libcap.m4 \ + $(top_srcdir)/aclocal/libevent.m4 \ + $(top_srcdir)/aclocal/libpthread.m4 \ + $(top_srcdir)/aclocal/libsqlite3.m4 \ + $(top_srcdir)/aclocal/libtirpc.m4 \ + $(top_srcdir)/aclocal/libxml2.m4 \ + $(top_srcdir)/aclocal/nfs-utils.m4 \ + $(top_srcdir)/aclocal/rpcsec_vers.m4 \ + $(top_srcdir)/aclocal/tcp-wrappers.m4 \ + $(top_srcdir)/configure.ac +am__configure_deps = $(am__aclocal_m4_deps) $(CONFIGURE_DEPENDENCIES) \ + $(ACLOCAL_M4) +DIST_COMMON = $(srcdir)/Makefile.am $(am__DIST_COMMON) +mkinstalldirs = $(install_sh) -d +CONFIG_HEADER = $(top_builddir)/support/include/config.h +CONFIG_CLEAN_FILES = +CONFIG_CLEAN_VPATH_FILES = +am__installdirs = "$(DESTDIR)$(sbindir)" "$(DESTDIR)$(man5dir)" \ + "$(DESTDIR)$(man7dir)" "$(DESTDIR)$(man8dir)" +PROGRAMS = $(sbin_PROGRAMS) +am_exportfs_OBJECTS = exportfs-exportfs.$(OBJEXT) +exportfs_OBJECTS = $(am_exportfs_OBJECTS) +am__DEPENDENCIES_1 = +exportfs_DEPENDENCIES = ../../support/export/libexport.a \ + ../../support/nfs/libnfs.la ../../support/misc/libmisc.a \ + ../../support/reexport/libreexport.a $(am__DEPENDENCIES_1) \ + $(am__DEPENDENCIES_1) $(am__DEPENDENCIES_1) +AM_V_lt = $(am__v_lt_@AM_V@) +am__v_lt_ = $(am__v_lt_@AM_DEFAULT_V@) +am__v_lt_0 = --silent +am__v_lt_1 = +AM_V_P = $(am__v_P_@AM_V@) +am__v_P_ = $(am__v_P_@AM_DEFAULT_V@) +am__v_P_0 = false +am__v_P_1 = : +AM_V_GEN = $(am__v_GEN_@AM_V@) +am__v_GEN_ = $(am__v_GEN_@AM_DEFAULT_V@) +am__v_GEN_0 = @echo " GEN " $@; +am__v_GEN_1 = +AM_V_at = $(am__v_at_@AM_V@) +am__v_at_ = $(am__v_at_@AM_DEFAULT_V@) +am__v_at_0 = @ +am__v_at_1 = +DEFAULT_INCLUDES = -I.@am__isrc@ -I$(top_builddir)/support/include +depcomp = $(SHELL) $(top_srcdir)/depcomp +am__maybe_remake_depfiles = depfiles +am__depfiles_remade = ./$(DEPDIR)/exportfs-exportfs.Po +am__mv = mv -f +COMPILE = $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) \ + $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) +LTCOMPILE = $(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) \ + $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) \ + $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) \ + $(AM_CFLAGS) $(CFLAGS) +AM_V_CC = $(am__v_CC_@AM_V@) +am__v_CC_ = $(am__v_CC_@AM_DEFAULT_V@) +am__v_CC_0 = @echo " CC " $@; +am__v_CC_1 = +CCLD = $(CC) +LINK = $(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) \ + $(LIBTOOLFLAGS) --mode=link $(CCLD) $(AM_CFLAGS) $(CFLAGS) \ + $(AM_LDFLAGS) $(LDFLAGS) -o $@ +AM_V_CCLD = $(am__v_CCLD_@AM_V@) +am__v_CCLD_ = $(am__v_CCLD_@AM_DEFAULT_V@) +am__v_CCLD_0 = @echo " CCLD " $@; +am__v_CCLD_1 = +SOURCES = $(exportfs_SOURCES) +DIST_SOURCES = $(exportfs_SOURCES) +am__can_run_installinfo = \ + case $$AM_UPDATE_INFO_DIR in \ + n|no|NO) false;; \ + *) (install-info --version) >/dev/null 2>&1;; \ + esac +am__vpath_adj_setup = srcdirstrip=`echo "$(srcdir)" | sed 's|.|.|g'`; +am__vpath_adj = case $$p in \ + $(srcdir)/*) f=`echo "$$p" | sed "s|^$$srcdirstrip/||"`;; \ + *) f=$$p;; \ + esac; +am__strip_dir = f=`echo $$p | sed -e 's|^.*/||'`; +am__install_max = 40 +am__nobase_strip_setup = \ + srcdirstrip=`echo "$(srcdir)" | sed 's/[].[^$$\\*|]/\\\\&/g'` +am__nobase_strip = \ + for p in $$list; do echo "$$p"; done | sed -e "s|$$srcdirstrip/||" +am__nobase_list = $(am__nobase_strip_setup); \ + for p in $$list; do echo "$$p $$p"; done | \ + sed "s| $$srcdirstrip/| |;"' / .*\//!s/ .*/ ./; s,\( .*\)/[^/]*$$,\1,' | \ + $(AWK) 'BEGIN { files["."] = "" } { files[$$2] = files[$$2] " " $$1; \ + if (++n[$$2] == $(am__install_max)) \ + { print $$2, files[$$2]; n[$$2] = 0; files[$$2] = "" } } \ + END { for (dir in files) print dir, files[dir] }' +am__base_list = \ + sed '$$!N;$$!N;$$!N;$$!N;$$!N;$$!N;$$!N;s/\n/ /g' | \ + sed '$$!N;$$!N;$$!N;$$!N;s/\n/ /g' +am__uninstall_files_from_dir = { \ + test -z "$$files" \ + || { test ! -d "$$dir" && test ! -f "$$dir" && test ! -r "$$dir"; } \ + || { echo " ( cd '$$dir' && rm -f" $$files ")"; \ + $(am__cd) "$$dir" && rm -f $$files; }; \ + } +man5dir = $(mandir)/man5 +man7dir = $(mandir)/man7 +man8dir = $(mandir)/man8 +NROFF = nroff +MANS = $(man5_MANS) $(man7_MANS) $(man8_MANS) +am__tagged_files = $(HEADERS) $(SOURCES) $(TAGS_FILES) $(LISP) +# Read a list of newline-separated strings from the standard input, +# and print each of them once, without duplicates. Input order is +# *not* preserved. +am__uniquify_input = $(AWK) '\ + BEGIN { nonempty = 0; } \ + { items[$$0] = 1; nonempty = 1; } \ + END { if (nonempty) { for (i in items) print i; }; } \ +' +# Make sure the list of sources is unique. This is necessary because, +# e.g., the same source file might be shared among _SOURCES variables +# for different programs/libraries. +am__define_uniq_tagged_files = \ + list='$(am__tagged_files)'; \ + unique=`for i in $$list; do \ + if test -f "$$i"; then echo $$i; else echo $(srcdir)/$$i; fi; \ + done | $(am__uniquify_input)` +am__DIST_COMMON = $(srcdir)/Makefile.in $(top_srcdir)/depcomp +DISTFILES = $(DIST_COMMON) $(DIST_SOURCES) $(TEXINFOS) $(EXTRA_DIST) +ACLOCAL = @ACLOCAL@ +ACLOCAL_AMFLAGS = @ACLOCAL_AMFLAGS@ +ALLOCA = @ALLOCA@ +AMTAR = @AMTAR@ +AM_CFLAGS = @AM_CFLAGS@ +AM_CPPFLAGS = @AM_CPPFLAGS@ +AM_DEFAULT_VERBOSITY = @AM_DEFAULT_VERBOSITY@ +AR = @AR@ +AUTOCONF = @AUTOCONF@ +AUTOHEADER = @AUTOHEADER@ +AUTOMAKE = @AUTOMAKE@ +AWK = @AWK@ +CC = @CC@ +CCDEPMODE = @CCDEPMODE@ +CC_FOR_BUILD = @CC_FOR_BUILD@ +CFLAGS = @CFLAGS@ +CFLAGS_FOR_BUILD = @CFLAGS_FOR_BUILD@ +CPP = @CPP@ +CPPFLAGS = @CPPFLAGS@ +CPPFLAGS_FOR_BUILD = @CPPFLAGS_FOR_BUILD@ +CSCOPE = @CSCOPE@ +CTAGS = @CTAGS@ +CXX = @CXX@ +CXXCPP = @CXXCPP@ +CXXDEPMODE = @CXXDEPMODE@ +CXXFLAGS = @CXXFLAGS@ +CXXFLAGS_FOR_BUILD = @CXXFLAGS_FOR_BUILD@ +CYGPATH_W = @CYGPATH_W@ +DEFS = @DEFS@ +DEPDIR = @DEPDIR@ +DLLTOOL = @DLLTOOL@ +DSYMUTIL = @DSYMUTIL@ +DUMPBIN = @DUMPBIN@ +ECHO_C = @ECHO_C@ +ECHO_N = @ECHO_N@ +ECHO_T = @ECHO_T@ +EGREP = @EGREP@ +ETAGS = @ETAGS@ +EXEEXT = @EXEEXT@ +FGREP = @FGREP@ +FILECMD = @FILECMD@ +GREP = @GREP@ +GSSAPI_CFLAGS = @GSSAPI_CFLAGS@ +GSSAPI_LIBS = @GSSAPI_LIBS@ +GSSD = @GSSD@ +GSSGLUE_CFLAGS = @GSSGLUE_CFLAGS@ +GSSGLUE_LIBS = @GSSGLUE_LIBS@ +GSSKRB_CFLAGS = @GSSKRB_CFLAGS@ +GSSKRB_LIBS = @GSSKRB_LIBS@ +HAVE_GETRANDOM = @HAVE_GETRANDOM@ +HAVE_LIBWRAP = @HAVE_LIBWRAP@ +HAVE_TCP_WRAPPER = @HAVE_TCP_WRAPPER@ +IDMAPD = @IDMAPD@ +INSTALL = @INSTALL@ +INSTALL_DATA = @INSTALL_DATA@ +INSTALL_PROGRAM = @INSTALL_PROGRAM@ +INSTALL_SCRIPT = @INSTALL_SCRIPT@ +INSTALL_STRIP_PROGRAM = @INSTALL_STRIP_PROGRAM@ +K5VERS = @K5VERS@ +KRBCFLAGS = @KRBCFLAGS@ +KRBDIR = @KRBDIR@ +KRBLDFLAGS = @KRBLDFLAGS@ +KRBLIBS = @KRBLIBS@ +LD = @LD@ +LDFLAGS = @LDFLAGS@ +LDFLAGS_FOR_BUILD = @LDFLAGS_FOR_BUILD@ +LIBBLKID = @LIBBLKID@ +LIBBSD = @LIBBSD@ +LIBCAP = @LIBCAP@ +LIBCRYPT = @LIBCRYPT@ +LIBEVENT = @LIBEVENT@ +LIBKEYUTILS = @LIBKEYUTILS@ +LIBMOUNT = @LIBMOUNT@ +LIBMOUNT_CFLAGS = @LIBMOUNT_CFLAGS@ +LIBMOUNT_LIBS = @LIBMOUNT_LIBS@ +LIBNSL = @LIBNSL@ +LIBOBJS = @LIBOBJS@ +LIBPTHREAD = @LIBPTHREAD@ +LIBS = @LIBS@ +LIBSOCKET = @LIBSOCKET@ +LIBSQLITE = @LIBSQLITE@ +LIBTIRPC = @LIBTIRPC@ +LIBTOOL = @LIBTOOL@ +LIBWRAP = @LIBWRAP@ +LIBXML2 = @LIBXML2@ +LIPO = @LIPO@ +LN_S = @LN_S@ +LTLIBOBJS = @LTLIBOBJS@ +LT_SYS_LIBRARY_PATH = @LT_SYS_LIBRARY_PATH@ +MAINT = @MAINT@ +MAKEINFO = @MAKEINFO@ +MANIFEST_TOOL = @MANIFEST_TOOL@ +MKDIR_P = @MKDIR_P@ +NM = @NM@ +NMEDIT = @NMEDIT@ +OBJDUMP = @OBJDUMP@ +OBJEXT = @OBJEXT@ +OTOOL = @OTOOL@ +OTOOL64 = @OTOOL64@ +PACKAGE = @PACKAGE@ +PACKAGE_BUGREPORT = @PACKAGE_BUGREPORT@ +PACKAGE_NAME = @PACKAGE_NAME@ +PACKAGE_STRING = @PACKAGE_STRING@ +PACKAGE_TARNAME = @PACKAGE_TARNAME@ +PACKAGE_URL = @PACKAGE_URL@ +PACKAGE_VERSION = @PACKAGE_VERSION@ +PATH_PLUGINS = @PATH_PLUGINS@ +PATH_SEPARATOR = @PATH_SEPARATOR@ +PKG_CONFIG = @PKG_CONFIG@ +PKG_CONFIG_LIBDIR = @PKG_CONFIG_LIBDIR@ +PKG_CONFIG_PATH = @PKG_CONFIG_PATH@ +RANLIB = @RANLIB@ +RELEASE = @RELEASE@ +RPCGEN_PATH = @RPCGEN_PATH@ +RPCSECGSS_CFLAGS = @RPCSECGSS_CFLAGS@ +RPCSECGSS_LIBS = @RPCSECGSS_LIBS@ +SED = @SED@ +SET_MAKE = @SET_MAKE@ +SHELL = @SHELL@ +STRIP = @STRIP@ +SVCGSSD = @SVCGSSD@ +TIRPC_CFLAGS = @TIRPC_CFLAGS@ +TIRPC_LIBS = @TIRPC_LIBS@ +VERSION = @VERSION@ +XML2_CFLAGS = @XML2_CFLAGS@ +XML2_LIBS = @XML2_LIBS@ +_rpc_pipefsmount = @_rpc_pipefsmount@ +_statedir = @_statedir@ +_sysconfdir = @_sysconfdir@ +abs_builddir = @abs_builddir@ +abs_srcdir = @abs_srcdir@ +abs_top_builddir = @abs_top_builddir@ +abs_top_srcdir = @abs_top_srcdir@ +ac_ct_AR = @ac_ct_AR@ +ac_ct_CC = @ac_ct_CC@ +ac_ct_CXX = @ac_ct_CXX@ +ac_ct_DUMPBIN = @ac_ct_DUMPBIN@ +am__include = @am__include@ +am__leading_dot = @am__leading_dot@ +am__quote = @am__quote@ +am__tar = @am__tar@ +am__untar = @am__untar@ +bindir = @bindir@ +build = @build@ +build_alias = @build_alias@ +build_cpu = @build_cpu@ +build_os = @build_os@ +build_vendor = @build_vendor@ +builddir = @builddir@ +datadir = @datadir@ +datarootdir = @datarootdir@ +docdir = @docdir@ +dvidir = @dvidir@ +enable_gss = @enable_gss@ +enable_ipv6 = @enable_ipv6@ +enable_mountconfig = @enable_mountconfig@ +enable_nfsv4 = @enable_nfsv4@ +enable_nfsv41 = @enable_nfsv41@ +enable_svcgss = @enable_svcgss@ +exec_prefix = @exec_prefix@ +host = @host@ +host_alias = @host_alias@ +host_cpu = @host_cpu@ +host_os = @host_os@ +host_vendor = @host_vendor@ +htmldir = @htmldir@ +includedir = @includedir@ +infodir = @infodir@ +install_sh = @install_sh@ +kprefix = @kprefix@ +libdir = @libdir@ +libexecdir = @libexecdir@ +localedir = @localedir@ +localstatedir = @localstatedir@ +mandir = @mandir@ +mkdir_p = @mkdir_p@ +mountfile = @mountfile@ +nfsconfig = @nfsconfig@ +oldincludedir = @oldincludedir@ +pdfdir = @pdfdir@ +prefix = @prefix@ +program_transform_name = @program_transform_name@ +psdir = @psdir@ +rpc_pipefsmount = @rpc_pipefsmount@ +runstatedir = @runstatedir@ +sbindir = @sbindir@ +sharedstatedir = @sharedstatedir@ +srcdir = @srcdir@ +startstatd = @startstatd@ +statdpath = @statdpath@ +statduser = @statduser@ +statedir = @statedir@ +sysconfdir = @sysconfdir@ +target_alias = @target_alias@ +top_build_prefix = @top_build_prefix@ +top_builddir = @top_builddir@ +top_srcdir = @top_srcdir@ +unitdir = @unitdir@ +man5_MANS = exports.man +man7_MANS = nfsd.man +man8_MANS = exportfs.man +EXTRA_DIST = $(man5_MANS) $(man7_MANS) $(man8_MANS) +exportfs_SOURCES = exportfs.c +exportfs_LDADD = ../../support/export/libexport.a \ + ../../support/nfs/libnfs.la \ + ../../support/misc/libmisc.a \ + ../../support/reexport/libreexport.a \ + $(LIBWRAP) $(LIBNSL) $(LIBPTHREAD) + +exportfs_CPPFLAGS = $(AM_CPPFLAGS) $(CPPFLAGS) -I$(top_srcdir)/support/reexport +MAINTAINERCLEANFILES = Makefile.in +all: all-am + +.SUFFIXES: +.SUFFIXES: .c .lo .o .obj +$(srcdir)/Makefile.in: @MAINTAINER_MODE_TRUE@ $(srcdir)/Makefile.am $(am__configure_deps) + @for dep in $?; do \ + case '$(am__configure_deps)' in \ + *$$dep*) \ + ( cd $(top_builddir) && $(MAKE) $(AM_MAKEFLAGS) am--refresh ) \ + && { if test -f $@; then exit 0; else break; fi; }; \ + exit 1;; \ + esac; \ + done; \ + echo ' cd $(top_srcdir) && $(AUTOMAKE) --gnu utils/exportfs/Makefile'; \ + $(am__cd) $(top_srcdir) && \ + $(AUTOMAKE) --gnu utils/exportfs/Makefile +Makefile: $(srcdir)/Makefile.in $(top_builddir)/config.status + @case '$?' in \ + *config.status*) \ + cd $(top_builddir) && $(MAKE) $(AM_MAKEFLAGS) am--refresh;; \ + *) \ + echo ' cd $(top_builddir) && $(SHELL) ./config.status $(subdir)/$@ $(am__maybe_remake_depfiles)'; \ + cd $(top_builddir) && $(SHELL) ./config.status $(subdir)/$@ $(am__maybe_remake_depfiles);; \ + esac; + +$(top_builddir)/config.status: $(top_srcdir)/configure $(CONFIG_STATUS_DEPENDENCIES) + cd $(top_builddir) && $(MAKE) $(AM_MAKEFLAGS) am--refresh + +$(top_srcdir)/configure: @MAINTAINER_MODE_TRUE@ $(am__configure_deps) + cd $(top_builddir) && $(MAKE) $(AM_MAKEFLAGS) am--refresh +$(ACLOCAL_M4): @MAINTAINER_MODE_TRUE@ $(am__aclocal_m4_deps) + cd $(top_builddir) && $(MAKE) $(AM_MAKEFLAGS) am--refresh +$(am__aclocal_m4_deps): +install-sbinPROGRAMS: $(sbin_PROGRAMS) + @$(NORMAL_INSTALL) + @list='$(sbin_PROGRAMS)'; test -n "$(sbindir)" || list=; \ + if test -n "$$list"; then \ + echo " $(MKDIR_P) '$(DESTDIR)$(sbindir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(sbindir)" || exit 1; \ + fi; \ + for p in $$list; do echo "$$p $$p"; done | \ + sed 's/$(EXEEXT)$$//' | \ + while read p p1; do if test -f $$p \ + || test -f $$p1 \ + ; then echo "$$p"; echo "$$p"; else :; fi; \ + done | \ + sed -e 'p;s,.*/,,;n;h' \ + -e 's|.*|.|' \ + -e 'p;x;s,.*/,,;s/$(EXEEXT)$$//;$(transform);s/$$/$(EXEEXT)/' | \ + sed 'N;N;N;s,\n, ,g' | \ + $(AWK) 'BEGIN { files["."] = ""; dirs["."] = 1 } \ + { d=$$3; if (dirs[d] != 1) { print "d", d; dirs[d] = 1 } \ + if ($$2 == $$4) files[d] = files[d] " " $$1; \ + else { print "f", $$3 "/" $$4, $$1; } } \ + END { for (d in files) print "f", d, files[d] }' | \ + while read type dir files; do \ + if test "$$dir" = .; then dir=; else dir=/$$dir; fi; \ + test -z "$$files" || { \ + echo " $(INSTALL_PROGRAM_ENV) $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL_PROGRAM) $$files '$(DESTDIR)$(sbindir)$$dir'"; \ + $(INSTALL_PROGRAM_ENV) $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL_PROGRAM) $$files "$(DESTDIR)$(sbindir)$$dir" || exit $$?; \ + } \ + ; done + +uninstall-sbinPROGRAMS: + @$(NORMAL_UNINSTALL) + @list='$(sbin_PROGRAMS)'; test -n "$(sbindir)" || list=; \ + files=`for p in $$list; do echo "$$p"; done | \ + sed -e 'h;s,^.*/,,;s/$(EXEEXT)$$//;$(transform)' \ + -e 's/$$/$(EXEEXT)/' \ + `; \ + test -n "$$list" || exit 0; \ + echo " ( cd '$(DESTDIR)$(sbindir)' && rm -f" $$files ")"; \ + cd "$(DESTDIR)$(sbindir)" && rm -f $$files + +clean-sbinPROGRAMS: + @list='$(sbin_PROGRAMS)'; test -n "$$list" || exit 0; \ + echo " rm -f" $$list; \ + rm -f $$list || exit $$?; \ + test -n "$(EXEEXT)" || exit 0; \ + list=`for p in $$list; do echo "$$p"; done | sed 's/$(EXEEXT)$$//'`; \ + echo " rm -f" $$list; \ + rm -f $$list + +exportfs$(EXEEXT): $(exportfs_OBJECTS) $(exportfs_DEPENDENCIES) $(EXTRA_exportfs_DEPENDENCIES) + @rm -f exportfs$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(exportfs_OBJECTS) $(exportfs_LDADD) $(LIBS) + +mostlyclean-compile: + -rm -f *.$(OBJEXT) + +distclean-compile: + -rm -f *.tab.c + +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/exportfs-exportfs.Po@am__quote@ # am--include-marker + +$(am__depfiles_remade): + @$(MKDIR_P) $(@D) + @echo '# dummy' >$@-t && $(am__mv) $@-t $@ + +am--depfiles: $(am__depfiles_remade) + +.c.o: +@am__fastdepCC_TRUE@ $(AM_V_CC)$(COMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ $< +@am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Po +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(COMPILE) -c -o $@ $< + +.c.obj: +@am__fastdepCC_TRUE@ $(AM_V_CC)$(COMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ `$(CYGPATH_W) '$<'` +@am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Po +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(COMPILE) -c -o $@ `$(CYGPATH_W) '$<'` + +.c.lo: +@am__fastdepCC_TRUE@ $(AM_V_CC)$(LTCOMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ $< +@am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Plo +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=yes @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LTCOMPILE) -c -o $@ $< + +exportfs-exportfs.o: exportfs.c +@am__fastdepCC_TRUE@ $(AM_V_CC)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(exportfs_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT exportfs-exportfs.o -MD -MP -MF $(DEPDIR)/exportfs-exportfs.Tpo -c -o exportfs-exportfs.o `test -f 'exportfs.c' || echo '$(srcdir)/'`exportfs.c +@am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/exportfs-exportfs.Tpo $(DEPDIR)/exportfs-exportfs.Po +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='exportfs.c' object='exportfs-exportfs.o' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(exportfs_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o exportfs-exportfs.o `test -f 'exportfs.c' || echo '$(srcdir)/'`exportfs.c + +exportfs-exportfs.obj: exportfs.c +@am__fastdepCC_TRUE@ $(AM_V_CC)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(exportfs_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT exportfs-exportfs.obj -MD -MP -MF $(DEPDIR)/exportfs-exportfs.Tpo -c -o exportfs-exportfs.obj `if test -f 'exportfs.c'; then $(CYGPATH_W) 'exportfs.c'; else $(CYGPATH_W) '$(srcdir)/exportfs.c'; fi` +@am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/exportfs-exportfs.Tpo $(DEPDIR)/exportfs-exportfs.Po +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='exportfs.c' object='exportfs-exportfs.obj' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(exportfs_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o exportfs-exportfs.obj `if test -f 'exportfs.c'; then $(CYGPATH_W) 'exportfs.c'; else $(CYGPATH_W) '$(srcdir)/exportfs.c'; fi` + +mostlyclean-libtool: + -rm -f *.lo + +clean-libtool: + -rm -rf .libs _libs +install-man5: $(man5_MANS) + @$(NORMAL_INSTALL) + @list1='$(man5_MANS)'; \ + list2=''; \ + test -n "$(man5dir)" \ + && test -n "`echo $$list1$$list2`" \ + || exit 0; \ + echo " $(MKDIR_P) '$(DESTDIR)$(man5dir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(man5dir)" || exit 1; \ + { for i in $$list1; do echo "$$i"; done; \ + if test -n "$$list2"; then \ + for i in $$list2; do echo "$$i"; done \ + | sed -n '/\.5[a-z]*$$/p'; \ + fi; \ + } | while read p; do \ + if test -f $$p; then d=; else d="$(srcdir)/"; fi; \ + echo "$$d$$p"; echo "$$p"; \ + done | \ + sed -e 'n;s,.*/,,;p;h;s,.*\.,,;s,^[^5][0-9a-z]*$$,5,;x' \ + -e 's,\.[0-9a-z]*$$,,;$(transform);G;s,\n,.,' | \ + sed 'N;N;s,\n, ,g' | { \ + list=; while read file base inst; do \ + if test "$$base" = "$$inst"; then list="$$list $$file"; else \ + echo " $(INSTALL_DATA) '$$file' '$(DESTDIR)$(man5dir)/$$inst'"; \ + $(INSTALL_DATA) "$$file" "$(DESTDIR)$(man5dir)/$$inst" || exit $$?; \ + fi; \ + done; \ + for i in $$list; do echo "$$i"; done | $(am__base_list) | \ + while read files; do \ + test -z "$$files" || { \ + echo " $(INSTALL_DATA) $$files '$(DESTDIR)$(man5dir)'"; \ + $(INSTALL_DATA) $$files "$(DESTDIR)$(man5dir)" || exit $$?; }; \ + done; } + +uninstall-man5: + @$(NORMAL_UNINSTALL) + @list='$(man5_MANS)'; test -n "$(man5dir)" || exit 0; \ + files=`{ for i in $$list; do echo "$$i"; done; \ + } | sed -e 's,.*/,,;h;s,.*\.,,;s,^[^5][0-9a-z]*$$,5,;x' \ + -e 's,\.[0-9a-z]*$$,,;$(transform);G;s,\n,.,'`; \ + dir='$(DESTDIR)$(man5dir)'; $(am__uninstall_files_from_dir) +install-man7: $(man7_MANS) + @$(NORMAL_INSTALL) + @list1='$(man7_MANS)'; \ + list2=''; \ + test -n "$(man7dir)" \ + && test -n "`echo $$list1$$list2`" \ + || exit 0; \ + echo " $(MKDIR_P) '$(DESTDIR)$(man7dir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(man7dir)" || exit 1; \ + { for i in $$list1; do echo "$$i"; done; \ + if test -n "$$list2"; then \ + for i in $$list2; do echo "$$i"; done \ + | sed -n '/\.7[a-z]*$$/p'; \ + fi; \ + } | while read p; do \ + if test -f $$p; then d=; else d="$(srcdir)/"; fi; \ + echo "$$d$$p"; echo "$$p"; \ + done | \ + sed -e 'n;s,.*/,,;p;h;s,.*\.,,;s,^[^7][0-9a-z]*$$,7,;x' \ + -e 's,\.[0-9a-z]*$$,,;$(transform);G;s,\n,.,' | \ + sed 'N;N;s,\n, ,g' | { \ + list=; while read file base inst; do \ + if test "$$base" = "$$inst"; then list="$$list $$file"; else \ + echo " $(INSTALL_DATA) '$$file' '$(DESTDIR)$(man7dir)/$$inst'"; \ + $(INSTALL_DATA) "$$file" "$(DESTDIR)$(man7dir)/$$inst" || exit $$?; \ + fi; \ + done; \ + for i in $$list; do echo "$$i"; done | $(am__base_list) | \ + while read files; do \ + test -z "$$files" || { \ + echo " $(INSTALL_DATA) $$files '$(DESTDIR)$(man7dir)'"; \ + $(INSTALL_DATA) $$files "$(DESTDIR)$(man7dir)" || exit $$?; }; \ + done; } + +uninstall-man7: + @$(NORMAL_UNINSTALL) + @list='$(man7_MANS)'; test -n "$(man7dir)" || exit 0; \ + files=`{ for i in $$list; do echo "$$i"; done; \ + } | sed -e 's,.*/,,;h;s,.*\.,,;s,^[^7][0-9a-z]*$$,7,;x' \ + -e 's,\.[0-9a-z]*$$,,;$(transform);G;s,\n,.,'`; \ + dir='$(DESTDIR)$(man7dir)'; $(am__uninstall_files_from_dir) +install-man8: $(man8_MANS) + @$(NORMAL_INSTALL) + @list1='$(man8_MANS)'; \ + list2=''; \ + test -n "$(man8dir)" \ + && test -n "`echo $$list1$$list2`" \ + || exit 0; \ + echo " $(MKDIR_P) '$(DESTDIR)$(man8dir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(man8dir)" || exit 1; \ + { for i in $$list1; do echo "$$i"; done; \ + if test -n "$$list2"; then \ + for i in $$list2; do echo "$$i"; done \ + | sed -n '/\.8[a-z]*$$/p'; \ + fi; \ + } | while read p; do \ + if test -f $$p; then d=; else d="$(srcdir)/"; fi; \ + echo "$$d$$p"; echo "$$p"; \ + done | \ + sed -e 'n;s,.*/,,;p;h;s,.*\.,,;s,^[^8][0-9a-z]*$$,8,;x' \ + -e 's,\.[0-9a-z]*$$,,;$(transform);G;s,\n,.,' | \ + sed 'N;N;s,\n, ,g' | { \ + list=; while read file base inst; do \ + if test "$$base" = "$$inst"; then list="$$list $$file"; else \ + echo " $(INSTALL_DATA) '$$file' '$(DESTDIR)$(man8dir)/$$inst'"; \ + $(INSTALL_DATA) "$$file" "$(DESTDIR)$(man8dir)/$$inst" || exit $$?; \ + fi; \ + done; \ + for i in $$list; do echo "$$i"; done | $(am__base_list) | \ + while read files; do \ + test -z "$$files" || { \ + echo " $(INSTALL_DATA) $$files '$(DESTDIR)$(man8dir)'"; \ + $(INSTALL_DATA) $$files "$(DESTDIR)$(man8dir)" || exit $$?; }; \ + done; } + +uninstall-man8: + @$(NORMAL_UNINSTALL) + @list='$(man8_MANS)'; test -n "$(man8dir)" || exit 0; \ + files=`{ for i in $$list; do echo "$$i"; done; \ + } | sed -e 's,.*/,,;h;s,.*\.,,;s,^[^8][0-9a-z]*$$,8,;x' \ + -e 's,\.[0-9a-z]*$$,,;$(transform);G;s,\n,.,'`; \ + dir='$(DESTDIR)$(man8dir)'; $(am__uninstall_files_from_dir) + +ID: $(am__tagged_files) + $(am__define_uniq_tagged_files); mkid -fID $$unique +tags: tags-am +TAGS: tags + +tags-am: $(TAGS_DEPENDENCIES) $(am__tagged_files) + set x; \ + here=`pwd`; \ + $(am__define_uniq_tagged_files); \ + shift; \ + if test -z "$(ETAGS_ARGS)$$*$$unique"; then :; else \ + test -n "$$unique" || unique=$$empty_fix; \ + if test $$# -gt 0; then \ + $(ETAGS) $(ETAGSFLAGS) $(AM_ETAGSFLAGS) $(ETAGS_ARGS) \ + "$$@" $$unique; \ + else \ + $(ETAGS) $(ETAGSFLAGS) $(AM_ETAGSFLAGS) $(ETAGS_ARGS) \ + $$unique; \ + fi; \ + fi +ctags: ctags-am + +CTAGS: ctags +ctags-am: $(TAGS_DEPENDENCIES) $(am__tagged_files) + $(am__define_uniq_tagged_files); \ + test -z "$(CTAGS_ARGS)$$unique" \ + || $(CTAGS) $(CTAGSFLAGS) $(AM_CTAGSFLAGS) $(CTAGS_ARGS) \ + $$unique + +GTAGS: + here=`$(am__cd) $(top_builddir) && pwd` \ + && $(am__cd) $(top_srcdir) \ + && gtags -i $(GTAGS_ARGS) "$$here" +cscopelist: cscopelist-am + +cscopelist-am: $(am__tagged_files) + list='$(am__tagged_files)'; \ + case "$(srcdir)" in \ + [\\/]* | ?:[\\/]*) sdir="$(srcdir)" ;; \ + *) sdir=$(subdir)/$(srcdir) ;; \ + esac; \ + for i in $$list; do \ + if test -f "$$i"; then \ + echo "$(subdir)/$$i"; \ + else \ + echo "$$sdir/$$i"; \ + fi; \ + done >> $(top_builddir)/cscope.files + +distclean-tags: + -rm -f TAGS ID GTAGS GRTAGS GSYMS GPATH tags +distdir: $(BUILT_SOURCES) + $(MAKE) $(AM_MAKEFLAGS) distdir-am + +distdir-am: $(DISTFILES) + @srcdirstrip=`echo "$(srcdir)" | sed 's/[].[^$$\\*]/\\\\&/g'`; \ + topsrcdirstrip=`echo "$(top_srcdir)" | sed 's/[].[^$$\\*]/\\\\&/g'`; \ + list='$(DISTFILES)'; \ + dist_files=`for file in $$list; do echo $$file; done | \ + sed -e "s|^$$srcdirstrip/||;t" \ + -e "s|^$$topsrcdirstrip/|$(top_builddir)/|;t"`; \ + case $$dist_files in \ + */*) $(MKDIR_P) `echo "$$dist_files" | \ + sed '/\//!d;s|^|$(distdir)/|;s,/[^/]*$$,,' | \ + sort -u` ;; \ + esac; \ + for file in $$dist_files; do \ + if test -f $$file || test -d $$file; then d=.; else d=$(srcdir); fi; \ + if test -d $$d/$$file; then \ + dir=`echo "/$$file" | sed -e 's,/[^/]*$$,,'`; \ + if test -d "$(distdir)/$$file"; then \ + find "$(distdir)/$$file" -type d ! -perm -700 -exec chmod u+rwx {} \;; \ + fi; \ + if test -d $(srcdir)/$$file && test $$d != $(srcdir); then \ + cp -fpR $(srcdir)/$$file "$(distdir)$$dir" || exit 1; \ + find "$(distdir)/$$file" -type d ! -perm -700 -exec chmod u+rwx {} \;; \ + fi; \ + cp -fpR $$d/$$file "$(distdir)$$dir" || exit 1; \ + else \ + test -f "$(distdir)/$$file" \ + || cp -p $$d/$$file "$(distdir)/$$file" \ + || exit 1; \ + fi; \ + done +check-am: all-am +check: check-am +all-am: Makefile $(PROGRAMS) $(MANS) +installdirs: + for dir in "$(DESTDIR)$(sbindir)" "$(DESTDIR)$(man5dir)" "$(DESTDIR)$(man7dir)" "$(DESTDIR)$(man8dir)"; do \ + test -z "$$dir" || $(MKDIR_P) "$$dir"; \ + done +install: install-am +install-exec: install-exec-am +install-data: install-data-am +uninstall: uninstall-am + +install-am: all-am + @$(MAKE) $(AM_MAKEFLAGS) install-exec-am install-data-am + +installcheck: installcheck-am +install-strip: + if test -z '$(STRIP)'; then \ + $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ + install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ + install; \ + else \ + $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ + install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ + "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'" install; \ + fi +mostlyclean-generic: + +clean-generic: + +distclean-generic: + -test -z "$(CONFIG_CLEAN_FILES)" || rm -f $(CONFIG_CLEAN_FILES) + -test . = "$(srcdir)" || test -z "$(CONFIG_CLEAN_VPATH_FILES)" || rm -f $(CONFIG_CLEAN_VPATH_FILES) + +maintainer-clean-generic: + @echo "This command is intended for maintainers to use" + @echo "it deletes files that may require special tools to rebuild." + -test -z "$(MAINTAINERCLEANFILES)" || rm -f $(MAINTAINERCLEANFILES) +clean: clean-am + +clean-am: clean-generic clean-libtool clean-sbinPROGRAMS \ + mostlyclean-am + +distclean: distclean-am + -rm -f ./$(DEPDIR)/exportfs-exportfs.Po + -rm -f Makefile +distclean-am: clean-am distclean-compile distclean-generic \ + distclean-tags + +dvi: dvi-am + +dvi-am: + +html: html-am + +html-am: + +info: info-am + +info-am: + +install-data-am: install-man + +install-dvi: install-dvi-am + +install-dvi-am: + +install-exec-am: install-sbinPROGRAMS + +install-html: install-html-am + +install-html-am: + +install-info: install-info-am + +install-info-am: + +install-man: install-man5 install-man7 install-man8 + +install-pdf: install-pdf-am + +install-pdf-am: + +install-ps: install-ps-am + +install-ps-am: + +installcheck-am: + +maintainer-clean: maintainer-clean-am + -rm -f ./$(DEPDIR)/exportfs-exportfs.Po + -rm -f Makefile +maintainer-clean-am: distclean-am maintainer-clean-generic + +mostlyclean: mostlyclean-am + +mostlyclean-am: mostlyclean-compile mostlyclean-generic \ + mostlyclean-libtool + +pdf: pdf-am + +pdf-am: + +ps: ps-am + +ps-am: + +uninstall-am: uninstall-man uninstall-sbinPROGRAMS + +uninstall-man: uninstall-man5 uninstall-man7 uninstall-man8 + +.MAKE: install-am install-strip + +.PHONY: CTAGS GTAGS TAGS all all-am am--depfiles check check-am clean \ + clean-generic clean-libtool clean-sbinPROGRAMS cscopelist-am \ + ctags ctags-am distclean distclean-compile distclean-generic \ + distclean-libtool distclean-tags distdir dvi dvi-am html \ + html-am info info-am install install-am install-data \ + install-data-am install-dvi install-dvi-am install-exec \ + install-exec-am install-html install-html-am install-info \ + install-info-am install-man install-man5 install-man7 \ + install-man8 install-pdf install-pdf-am install-ps \ + install-ps-am install-sbinPROGRAMS install-strip installcheck \ + installcheck-am installdirs maintainer-clean \ + maintainer-clean-generic mostlyclean mostlyclean-compile \ + mostlyclean-generic mostlyclean-libtool pdf pdf-am ps ps-am \ + tags tags-am uninstall uninstall-am uninstall-man \ + uninstall-man5 uninstall-man7 uninstall-man8 \ + uninstall-sbinPROGRAMS + +.PRECIOUS: Makefile + + +# Tell versions [3.59,3.63) of GNU make to not export all variables. +# Otherwise a system limit (for SysV at least) may be exceeded. +.NOEXPORT: diff --git a/utils/exportfs/exportfs.c b/utils/exportfs/exportfs.c new file mode 100644 index 0000000..b03a047 --- /dev/null +++ b/utils/exportfs/exportfs.c @@ -0,0 +1,768 @@ +/* + * utils/exportfs/exportfs.c + * + * Export file systems to knfsd + * + * Copyright (C) 1995, 1996, 1997 Olaf Kirch + * + * Extensive changes, 1999, Neil Brown + */ + +#ifdef HAVE_CONFIG_H +#include +#endif + +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include + +#define INT_TO_LONG_THRESHOLD_SECS (INT_MAX - (60 * 60 * 24)) + +#include "sockaddr.h" +#include "misc.h" +#include "nfsd_path.h" +#include "nfslib.h" +#include "exportfs.h" +#include "xlog.h" +#include "conffile.h" +#include "reexport.h" + +static void export_all(int verbose); +static void exportfs(char *arg, char *options, int verbose); +static void unexportfs(char *arg, int verbose); +static void dump(int verbose, int export_format); +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 void grab_lockfile(void); +static void release_lockfile(void); + +static const char *lockfile = EXP_LOCKFILE; +static int _lockfd = -1; + +/* + * If we aren't careful, changes made by exportfs can be lost + * when multiple exports process run at once: + * + * exportfs process 1 exportfs process 2 + * ------------------------------------------ + * reads etab version A reads etab version A + * adds new export B adds new export C + * writes A+B writes A+C + * + * The locking in support/export/xtab.c will prevent mountd from + * seeing a partially written version of etab, and will prevent + * the two writers above from writing simultaneously and + * corrupting etab, but to prevent problems like the above we + * need these additional lockfile() routines. + */ +static void +grab_lockfile(void) +{ + _lockfd = open(lockfile, O_CREAT|O_RDWR, 0666); + if (_lockfd != -1) + lockf(_lockfd, F_LOCK, 0); +} +static void +release_lockfile(void) +{ + if (_lockfd != -1) { + lockf(_lockfd, F_ULOCK, 0); + close(_lockfd); + _lockfd = -1; + } +} +inline static void +read_exportfs_conf(char **argv) +{ + char *s; + + conf_init_file(NFS_CONFFILE); + xlog_set_debug("exportfs"); + + /* NOTE: following uses "mountd" section of nfs.conf !!!! */ + s = conf_get_str("mountd", "state-directory-path"); + /* Also look in the exportd section */ + if (s == NULL) + s = conf_get_str("exportd", "state-directory-path"); + if (s && !state_setup_basedir(argv[0], s)) + exit(1); + +} +int +main(int argc, char **argv) +{ + char *options = NULL; + char *progname = NULL; + int f_export = 1; + int f_all = 0; + int f_verbose = 0; + int f_export_format = 0; + int f_reexport = 0; + int f_ignore = 0; + int i, c; + int force_flush = 0; + + if ((progname = strrchr(argv[0], '/')) != NULL) + progname++; + else + progname = argv[0]; + + xlog_open(progname); + xlog_stderr(1); + xlog_syslog(0); + + /* Read in config setting */ + read_exportfs_conf(argv); + + nfsd_path_init(); + + while ((c = getopt(argc, argv, "ad:fhio:ruvs")) != EOF) { + switch(c) { + case 'a': + f_all = 1; + break; + case 'd': + xlog_sconfig(optarg, 1); + break; + case 'f': + force_flush = 1; + break; + case 'h': + usage(progname, 0); + break; + case 'i': + f_ignore = 1; + break; + case 'o': + options = optarg; + break; + case 'r': + f_reexport = 1; + f_all = 1; + break; + case 'u': + f_export = 0; + break; + case 'v': + f_verbose = 1; + break; + case 's': + f_export_format = 1; + break; + default: + usage(progname, 1); + break; + } + } + + if (optind != argc && f_all) { + xlog(L_ERROR, "extra arguments are not permitted with -a or -r"); + return 1; + } + if (f_ignore && (f_all || ! f_export)) { + xlog(L_ERROR, "-i not meaningful with -a, -r or -u"); + return 1; + } + if (f_reexport && ! f_export) { + xlog(L_ERROR, "-r and -u are incompatible"); + return 1; + } + + if (!setup_state_path_names(progname, ETAB, ETABTMP, ETABLCK, &etab)) + return 1; + + if (optind == argc && ! f_all) { + if (force_flush) { + cache_flush(); + free_state_path_names(&etab); + return 0; + } else { + xtab_export_read(); + dump(f_verbose, f_export_format); + free_state_path_names(&etab); + export_freeall(); + return 0; + } + } + + /* + * Serialize things as best we can + */ + grab_lockfile(); + atexit(release_lockfile); + + if (f_export && ! f_ignore) { + if (! (export_read(_PATH_EXPORTS, 0) + + export_d_read(_PATH_EXPORTS_D, 0))) { + if (f_verbose) + xlog(L_WARNING, "No file systems exported!"); + } + } + if (f_export) { + if (f_all) + export_all(f_verbose); + else + for (i = optind; i < argc ; i++) + exportfs(argv[i], options, f_verbose); + } + /* If we are unexporting everything, then + * don't care about what should be exported, as that + * may require DNS lookups.. + */ + if (! ( !f_export && f_all)) { + /* note: xtab_*_read does not update entries if they already exist, + * so this will not lose new options + */ + if (!f_reexport) + xtab_export_read(); + if (!f_export) + for (i = optind ; i < argc ; i++) + unexportfs(argv[i], f_verbose); + } + xtab_export_write(); + cache_flush(); + free_state_path_names(&etab); + export_freeall(); + + return export_errno; +} + +/* + * export_all finds all entries and + * marks them xtabent and mayexport so that they get exported + */ +static void +export_all(int verbose) +{ + nfs_export *exp; + int i; + + for (i = 0; i < MCL_MAXTYPES; i++) { + for (exp = exportlist[i].p_head; exp; exp = exp->m_next) { + if (verbose) + printf("exporting %s:%s\n", + exp->m_client->m_hostname, + exp->m_export.e_path); + exp->m_xtabent = 1; + exp->m_mayexport = 1; + exp->m_changed = 1; + exp->m_warned = 0; + validate_export(exp); + } + } +} + + +static void +exportfs_parsed(char *hname, char *path, char *options, int verbose) +{ + struct exportent *eep; + nfs_export *exp = NULL; + struct addrinfo *ai = NULL; + int htype; + + if ((htype = client_gettype(hname)) == MCL_FQDN) { + ai = host_addrinfo(hname); + if (ai != NULL) { + exp = export_find(ai, path); + hname = ai->ai_canonname; + } + } else + exp = export_lookup(hname, path, 0); + + if (!exp) { + if (!(eep = mkexportent(hname, path, options)) || + !(exp = export_create(eep, 0))) + goto out; + } else if (!updateexportent(&exp->m_export, options)) + goto out; + + if (verbose) + printf("exporting %s:%s\n", exp->m_client->m_hostname, + exp->m_export.e_path); + exp->m_xtabent = 1; + exp->m_mayexport = 1; + exp->m_changed = 1; + exp->m_warned = 0; + validate_export(exp); + +out: + nfs_freeaddrinfo(ai); +} + +static int exportfs_generic(char *arg, char *options, int verbose) +{ + char *path; + + if ((path = strchr(arg, ':')) != NULL) + *path++ = '\0'; + + if (!path || *path != '/') + return 1; + + exportfs_parsed(arg, path, options, verbose); + return 0; +} + +static int exportfs_ipv6(char *arg, char *options, int verbose) +{ + char *path, *c; + + arg++; + c = strchr(arg, ']'); + if (c == NULL) + return 1; + + /* no colon means this is a wildcarded DNS hostname */ + if (memchr(arg, ':', c - arg) == NULL) + return exportfs_generic(--arg, options, verbose); + + path = strstr(c, ":/"); + if (path == NULL) + return 1; + *path++ = '\0'; + + /* if there's anything between the closing brace and the + * path separator, it's probably a prefix length */ + memmove(c, c + 1, path - c); + + exportfs_parsed(arg, path, options, verbose); + return 0; +} + +static void +exportfs(char *arg, char *options, int verbose) +{ + int failed; + + if (*arg == '[') + failed = exportfs_ipv6(arg, options, verbose); + else + failed = exportfs_generic(arg, options, verbose); + if (failed) + xlog(L_ERROR, "Invalid export syntax: %s", arg); +} + +static void +unexportfs_parsed(char *hname, char *path, int verbose) +{ + nfs_export *exp; + struct addrinfo *ai = NULL; + int htype; + int success = 0; + + if ((htype = client_gettype(hname)) == MCL_FQDN) { + ai = host_addrinfo(hname); + if (ai) + hname = ai->ai_canonname; + } + + /* + * It's possible the specified path ends with a '/'. But + * the entry from exportlist won't has the trailing '/', + * so need to deal with it. + */ + size_t nlen = strlen(path); + while ((nlen > 1) && (path[nlen - 1] == '/')) + nlen--; + + for (exp = exportlist[htype].p_head; exp; exp = exp->m_next) { + if (strlen(exp->m_export.e_path) != nlen) + continue; + if (path && strncmp(path, exp->m_export.e_path, nlen)) + continue; + if (htype != exp->m_client->m_type) + continue; + if (htype == MCL_FQDN + && !matchhostname(exp->m_export.e_hostname, + hname)) + continue; + if (htype != MCL_FQDN + && strcasecmp(exp->m_export.e_hostname, hname)) + continue; + if (verbose) { +#if 0 + if (exp->m_exported) { + printf("unexporting %s:%s from kernel\n", + exp->m_client->m_hostname, + exp->m_export.e_path); + } + else +#endif + printf("unexporting %s:%s\n", + exp->m_client->m_hostname, + exp->m_export.e_path); + } + exp->m_xtabent = 0; + exp->m_mayexport = 0; + success = 1; + } + if (!success) + xlog(L_ERROR, "Could not find '%s:%s' to unexport.", hname, path); + + nfs_freeaddrinfo(ai); +} + +static int unexportfs_generic(char *arg, int verbose) +{ + char *path; + + if ((path = strchr(arg, ':')) != NULL) + *path++ = '\0'; + + if (!path || *path != '/') + return 1; + + unexportfs_parsed(arg, path, verbose); + return 0; +} + +static int unexportfs_ipv6(char *arg, int verbose) +{ + char *path, *c; + + arg++; + c = strchr(arg, ']'); + if (c == NULL) + return 1; + + /* no colon means this is a wildcarded DNS hostname */ + if (memchr(arg, ':', c - arg) == NULL) + return unexportfs_generic(--arg, verbose); + + path = strstr(c, ":/"); + if (path == NULL) + return 1; + *path++ = '\0'; + + /* if there's anything between the closing brace and the + * path separator, it's probably a prefix length */ + memmove(c, c + 1, path - c); + + unexportfs_parsed(arg, path, verbose); + return 0; +} + +static void +unexportfs(char *arg, int verbose) +{ + int failed; + + if (*arg == '[') + failed = unexportfs_ipv6(arg, verbose); + else + failed = unexportfs_generic(arg, verbose); + if (failed) + xlog(L_ERROR, "Invalid export syntax: %s", arg); +} + +static int can_test(void) +{ + char buf[1024] = { 0 }; + int fd; + int n; + size_t bufsiz = sizeof(buf); + + fd = open("/proc/net/rpc/auth.unix.ip/channel", O_WRONLY); + if (fd < 0) + return 0; + + /* + * We introduce tolerance of 1 day to ensure that we use a + * LONG_MAX for the expiry timestamp before it is actually + * needed. To use LONG_MAX, the kernel code must have + * commit 2f74f972 (sunrpc: prepare NFS for 2038). + */ + if (time(NULL) > INT_TO_LONG_THRESHOLD_SECS) + snprintf(buf, bufsiz-1, "nfsd 0.0.0.0 %ld -test-client-\n", LONG_MAX); + else + snprintf(buf, bufsiz-1, "nfsd 0.0.0.0 %d -test-client-\n", INT_MAX); + + n = write(fd, buf, strlen(buf)); + close(fd); + if (n < 0) + return 0; + + fd = open("/proc/net/rpc/nfsd.export/channel", O_WRONLY); + if (fd < 0) + return 0; + close(fd); + return 1; +} + +static void +validate_export(nfs_export *exp) +{ + /* Check that the given export point is potentially exportable. + * We just give warnings here, don't cause anything to fail. + * If a path doesn't exist, or is not a dir or file, give an warning + * otherwise trial-export to '-test-client-' and check for failure. + */ + struct stat stb; + char *path = exportent_realpath(&exp->m_export); + struct statfs stf; + int fs_has_fsid = 0; + + if (stat(path, &stb) < 0) { + xlog(L_ERROR, "Failed to stat %s: %m", path); + return; + } + if (!S_ISDIR(stb.st_mode)) { + xlog(L_ERROR, "%s is not a directory. " + "Remote access will fail", path); + return; + } + if (!can_test()) + return; + + if (!statfs(path, &stf) && + (stf.f_fsid.__val[0] || stf.f_fsid.__val[1])) + fs_has_fsid = 1; + + if ((exp->m_export.e_flags & NFSEXP_FSID) || exp->m_export.e_uuid || + fs_has_fsid) { + if ( !export_test(&exp->m_export, 1)) { + xlog(L_ERROR, "%s does not support NFS export", path); + return; + } + } else if ( !export_test(&exp->m_export, 0)) { + if (export_test(&exp->m_export, 1)) + xlog(L_ERROR, "%s requires fsid= for NFS export", path); + else + xlog(L_ERROR, "%s does not support NFS export", path); + return; + + } +} + +static _Bool +is_hostname(const char *sp) +{ + if (*sp == '\0' || *sp == '@') + return false; + + for (; *sp != '\0'; sp++) { + if (*sp == '*' || *sp == '?' || *sp == '[' || *sp == '/') + return false; + if (*sp == '\\' && sp[1] != '\0') + sp++; + } + + return true; +} + +/* + * Take care to perform an explicit reverse lookup on presentation + * addresses. Otherwise we don't get a real canonical name or a + * complete list of addresses. + */ +static struct addrinfo * +address_list(const char *hostname) +{ + struct addrinfo *ai; + char *cname; + + ai = host_pton(hostname); + if (ai != NULL) { + /* @hostname was a presentation address */ + cname = host_canonname(ai->ai_addr); + nfs_freeaddrinfo(ai); + if (cname != NULL) + goto out; + } + /* @hostname was a hostname or had no reverse mapping */ + cname = strdup(hostname); + if (cname == NULL) + return NULL; + +out: + ai = host_addrinfo(cname); + free(cname); + return ai; +} + +static int +matchhostname(const char *hostname1, const char *hostname2) +{ + struct addrinfo *results1 = NULL, *results2 = NULL; + struct addrinfo *ai1, *ai2; + int result = 0; + + if (strcasecmp(hostname1, hostname2) == 0) + return 1; + + /* + * Don't pass export wildcards or netgroup names to DNS + */ + if (!is_hostname(hostname1) || !is_hostname(hostname2)) + return 0; + + results1 = address_list(hostname1); + if (results1 == NULL) + goto out; + results2 = address_list(hostname2); + if (results2 == NULL) + goto out; + + if (strcasecmp(results1->ai_canonname, results2->ai_canonname) == 0) { + result = 1; + goto out; + } + + for (ai1 = results1; ai1 != NULL; ai1 = ai1->ai_next) + for (ai2 = results2; ai2 != NULL; ai2 = ai2->ai_next) + if (nfs_compare_sockaddr(ai1->ai_addr, ai2->ai_addr)) { + result = 1; + break; + } + +out: + nfs_freeaddrinfo(results1); + nfs_freeaddrinfo(results2); + return result; +} + +#ifdef HAVE_FUNC_ATTRIBUTE_FORMAT +__attribute__((format (printf, 2, 3))) +#endif +static char +dumpopt(char c, char *fmt, ...) +{ + va_list ap; + + va_start(ap, fmt); + printf("%c", c); + vprintf(fmt, ap); + va_end(ap); + return ','; +} + +static void +dump(int verbose, int export_format) +{ + /* buf[] size should >= sizeof(struct exportent->e_path) */ + char buf[NFS_MAXPATHLEN+1] = { 0 }; + char *bp; + int len; + nfs_export *exp; + struct exportent *ep; + int htype; + char *hname, c; + + for (htype = 0; htype < MCL_MAXTYPES; htype++) { + for (exp = exportlist[htype].p_head; exp; exp = exp->m_next) { + ep = &exp->m_export; + if (!exp->m_xtabent) + continue; /* neilb */ + if (htype == MCL_ANONYMOUS) + hname = (export_format) ? "*" : ""; + else + hname = ep->e_hostname; + if (strlen(ep->e_path) > 14 && !export_format) + printf("%-14s\n\t\t%s", ep->e_path, hname); + else + if (export_format) { + bp = buf; + len = sizeof(buf) - 1; + qword_add(&bp, &len, ep->e_path); + *bp = '\0'; + printf("%s %s", buf, hname); + } else { + printf("%-14s\t%s", ep->e_path, hname); + } + + if (!verbose && !export_format) { + printf("\n"); + continue; + } + c = '('; + if (ep->e_flags & NFSEXP_ASYNC) + c = dumpopt(c, "async"); + else + c = dumpopt(c, "sync"); + if (ep->e_flags & NFSEXP_GATHERED_WRITES) + c = dumpopt(c, "wdelay"); + else + c = dumpopt(c, "no_wdelay"); + if (ep->e_flags & NFSEXP_NOHIDE) + c = dumpopt(c, "nohide"); + else + c = dumpopt(c, "hide"); + if (ep->e_flags & NFSEXP_CROSSMOUNT) + c = dumpopt(c, "crossmnt"); + if (ep->e_flags & NFSEXP_NOSUBTREECHECK) + c = dumpopt(c, "no_subtree_check"); + if (ep->e_flags & NFSEXP_NOAUTHNLM) + c = dumpopt(c, "insecure_locks"); + if (ep->e_flags & NFSEXP_NOREADDIRPLUS) + c = dumpopt(c, "nordirplus"); + if (ep->e_flags & NFSEXP_SECURITY_LABEL) + c = dumpopt(c, "security_label"); + if (ep->e_flags & NFSEXP_NOACL) + c = dumpopt(c, "no_acl"); + if (ep->e_flags & NFSEXP_PNFS) + c = dumpopt(c, "pnfs"); + if (ep->e_flags & NFSEXP_FSID) + c = dumpopt(c, "fsid=%d", ep->e_fsid); + if (ep->e_uuid) + c = dumpopt(c, "fsid=%s", ep->e_uuid); + if (ep->e_reexport) { + switch (ep->e_reexport) { + case REEXP_AUTO_FSIDNUM: + c = dumpopt(c, "reexport=%s", "auto-fsidnum"); + break; + case REEXP_PREDEFINED_FSIDNUM: + c = dumpopt(c, "reexport=%s", "predefined-fsidnum"); + break; + } + } + if (ep->e_mountpoint) + c = dumpopt(c, "mountpoint%s%s", + ep->e_mountpoint[0]?"=":"", + ep->e_mountpoint); + if (ep->e_anonuid != 65534) + c = dumpopt(c, "anonuid=%d", ep->e_anonuid); + if (ep->e_anongid != 65534) + c = dumpopt(c, "anongid=%d", ep->e_anongid); + switch(ep->e_fslocmethod) { + case FSLOC_NONE: + break; + case FSLOC_REFER: + c = dumpopt(c, "refer=%s", ep->e_fslocdata); + break; + case FSLOC_REPLICA: + c = dumpopt(c, "replicas=%s", ep->e_fslocdata); + break; +#ifdef DEBUG + case FSLOC_STUB: + c = dumpopt(c, "fsloc=stub"); + break; +#endif + } + secinfo_show(stdout, ep); + xprtsecinfo_show(stdout, ep); + printf("%c\n", (c != '(')? ')' : ' '); + } + } +} + +static void +usage(const char *progname, int n) +{ + fprintf(stderr, "usage: %s [-adfhioruvs] [host:/path]\n", progname); + exit(n); +} diff --git a/utils/exportfs/exportfs.man b/utils/exportfs/exportfs.man new file mode 100644 index 0000000..6d417a7 --- /dev/null +++ b/utils/exportfs/exportfs.man @@ -0,0 +1,337 @@ +.\"@(#)exportfs.8" +.\" +.\" Copyright (C) 1995 Olaf Kirch +.\" Modifications 1999-2003 Neil Brown +.\" +.TH exportfs 8 "30 September 2013" +.SH NAME +exportfs \- maintain table of exported NFS file systems +.SH SYNOPSIS +.BI "/usr/sbin/exportfs [-avi] [-o " "options,.." "] [" "client:/path" " ..] +.br +.BI "/usr/sbin/exportfs -r [-v]" +.br +.BI "/usr/sbin/exportfs [-av] -u [" "client:/path" " ..] +.br +.BI "/usr/sbin/exportfs [-v] +.br +.BI "/usr/sbin/exportfs -f" +.br +.BI "/usr/sbin/exportfs -s" +.br +.SH DESCRIPTION +An NFS server maintains a table of local physical file systems +that are accessible to NFS clients. +Each file system in this table is referred to as an +.IR "exported file system" , +or +.IR export , +for short. +.PP +The +.B exportfs +command maintains the current table of exports for the NFS server. +The master export table is kept in a file named +.IR /var/lib/nfs/etab . +This file is read by +.B rpc.mountd +when a client sends an NFS MOUNT request. +.PP +Normally the master export table is initialized with the contents of +.I /etc/exports +and files under +.I /etc/exports.d +by invoking +.BR "exportfs -a" . +However, a system administrator can choose to add or delete +exports without modifying +.I /etc/exports +or files under +.I /etc/exports.d +by using the +.B exportfs +command. +.PP +.B exportfs +and its partner program +.B rpc.mountd +work in one of two modes: a legacy mode which applies to 2.4 and +earlier versions of the Linux kernel, and a new mode which applies to +2.6 and later versions, providing the +.B nfsd +virtual filesystem has been mounted at +.I /proc/fs/nfsd +or +.IR /proc/fs/nfs . +On 2.6 kernels, if this filesystem is not mounted, the legacy mode is used. +.PP +In the new mode, +.B exportfs +does not give any information to the kernel, but provides it only to +.B rpc.mountd +through the +.I /var/lib/nfs/etab +file. +.B rpc.mountd +then manages kernel requests for information about exports, as needed. +.PP +In the legacy mode, +exports which identify a specific host, rather than a subnet or netgroup, +are entered directly into the kernel's export table, +as well as being written to +.IR /var/lib/nfs/etab . +Further, exports listed in +.I /var/lib/nfs/rmtab +which match a non host-specific export request will cause an +appropriate export entry for the host given in +.I rmtab +to be added to the kernel's export table. +.SH OPTIONS +.TP +.B \-d kind " or " \-\-debug kind +Turn on debugging. Valid kinds are: all, auth, call, general and parse. +Debugging can also be turned on by setting +.B debug= +in the +.B [exportfs] +section of +.IR /etc/nfs.conf . + +.TP +.B -a +Export or unexport all directories. +.TP +.BI "-o " options,... +Specify a list of export options in the same manner as in +.BR exports (5). +.TP +.B -i +Ignore the +.I /etc/exports +file and files under +.I /etc/exports.d +directory. Only default options and options given on the command line are used. +.TP +.B -r +Reexport all directories, synchronizing +.I /var/lib/nfs/etab +with +.IR /etc/exports +and files under +.IR /etc/exports.d . +This option removes entries in +.I /var/lib/nfs/etab +which have been deleted from +.I /etc/exports +or files under +.IR /etc/exports.d , +and removes any entries from the +kernel export table which are no longer valid. +.TP +.B -u +Unexport one or more directories. +.TP +.B -f +If +.I /proc/fs/nfsd +or +.I /proc/fs/nfs +is mounted, flush everything out of the kernel's export table. +Fresh entries for active clients are added to the kernel's export table by +.B rpc.mountd +when they make their next NFS mount request. +.TP +.B -v +Be verbose. When exporting or unexporting, show what's going on. When +displaying the current export list, also display the list of export +options. +.TP +.B -s +Display the current export list suitable for /etc/exports. + +.SH CONFIGURATION FILE +The +.B [exportfs] +section of the +.I /etc/nfs.conf +configuration file can contain a +.B debug +value, which can be one or more from the list +.BR general , +.BR call , +.BR auth , +.BR parse , +.BR all . +When a list is given, the members should be comma-separated. + +.B exportfs +will also recognize the +.B state-directory-path +value from both the +.B [mountd] +section and the +.B [exportd] +section + +.SH DISCUSSION +.SS Exporting Directories +The first synopsis shows how to invoke +.B exportfs +when adding new entries to the export table. When using +.BR "exportfs -a" , +all exports listed in +.I /etc/exports +and files under +.I /etc/exports.d +are added to +.IR /var/lib/nfs/etab . +The kernel's export table is also updated as needed. +.PP +The +.I host:/path +argument specifies a local directory to export, +along with the client or clients who are permitted to access it. +See +.B exports(5) +for a description of supported options and access list formats. +.PP +IPv6 presentation addresses contain colons, which are already used +to separate the "host" and "path" command line arguments. +When specifying a client using a raw IPv6 address, +enclose the address in square brackets. +For IPv6 network addresses, place the prefix just after the closing +bracket. +.PP +To export a directory to the world, simply specify +.IR :/path . +.PP +The export options for a particular host/directory pair derive from +several sources. +The default export options are +.BR sync,ro,root_squash,wdelay . +These can be overridden by entries in +.IR /etc/exports +or files under +.IR /etc/exports.d . +.PP +A system administrator may override options from these sources using the +.B -o +command-line option on +.BR exportfs . +This option takes a comma-separated list of options in the same fashion +as one would specify them in +.IR /etc/exports . +In this way +.B exportfs +can be used to modify the export options of an already exported directory. +.SS Unexporting Directories +The third synopsis shows how to unexport a currently exported directory. +When using +.BR "exportfs -ua" , +all entries listed in +.I /var/lib/nfs/etab +are removed from the kernel export tables, and the file is cleared. This +effectively shuts down all NFS activity. +.PP +To remove an export, specify a +.I host:/path +pair. This deletes the specified entry from +.I /var/lib/nfs/etab +and removes the corresponding kernel entry (if any). +.PP +.SS Dumping the Export Table +Invoking +.B exportfs +without options shows the current list of exported file systems. +Adding the +.B -v +option causes +.B exportfs +to display the export options for each export. +.SH EXAMPLES +The following adds all directories listed in +.I /etc/exports +and files under +.I /etc/exports.d +to +.I /var/lib/nfs/etab +and pushes the resulting export entries into the kernel: +.PP +.nf +.B "# exportfs -a +.fi +.PP +To export the +.I /usr/tmp +directory to host +.BR django , +allowing insecure file locking requests from clients: +.PP +.nf +.B "# exportfs -o insecure_locks django:/usr/tmp +.fi +.PP +To unexport the +.I /usr/tmp +directory: +.PP +.nf +.B "# exportfs -u django:/usr/tmp +.fi +.PP +To unexport all exports listed in +.IR /etc/exports +and files under +.IR /etc/exports.d : +.PP +.nf +.B "# exportfs -au +.fi +.PP +To export the +.I /usr/tmp +directory to IPv6 link-local clients: +.PP +.nf +.B "# exportfs [fe80::]/64:/usr/tmp +.fi +.SH USAGE NOTES +Exporting to IP networks or DNS and NIS domains does not enable clients +from these groups to access NFS immediately. +Rather, these sorts of exports are hints to +.BR rpc.mountd (8) +to grant any mount requests from these clients. +This is usually not a problem, because any existing mounts are preserved in +.I rmtab +across reboots. +.PP +When unexporting a network or domain entry, any current exports to members +of this group will be checked against the remaining valid exports and +if they themselves are no longer valid they will be removed. +.SH FILES +.TP 2.5i +.I /etc/exports +input file listing exports, export options, and access control lists +.TP 2.5i +.I /etc/exports.d +directory where extra input files are stored. +.B Note: +only files that end with +.I .exports +are used. +.TP 2.5i +.I /var/lib/nfs/etab +master table of exports +.TP 2.5i +.I /var/lib/nfs/rmtab +table of clients accessing server's exports +.SH SEE ALSO +.BR exports (5), +.BR nfs.conf (5), +.BR rpc.mountd (8), +.BR exportd (8), +.BR netgroup (5) +.SH AUTHORS +Olaf Kirch +.br +Neil Brown diff --git a/utils/exportfs/exports.man b/utils/exportfs/exports.man new file mode 100644 index 0000000..b758277 --- /dev/null +++ b/utils/exportfs/exports.man @@ -0,0 +1,678 @@ +.\"@(#)exports.5" +.\" +.TH exports 5 "31 December 2009" +.SH NAME +exports \- NFS server export table +.SH DESCRIPTION +The file +.I /etc/exports +contains a table of local physical file systems on an NFS server +that are accessible to NFS clients. +The contents of the file are maintained by the server's system +administrator. +.PP +Each file system in this table has a list of options and an +access control list. +The table is used by +.BR exportfs (8) +to give information to +.BR mountd (8). +.PP +The file format is similar to the SunOS +.I exports +file. Each line contains an export point and a whitespace-separated list +of clients allowed to mount the file system at that point. Each listed +client may be immediately followed by a parenthesized, comma-separated +list of export options for that client. No whitespace is permitted +between a client and its option list. +.PP +Also, each line may have one or more specifications for default options +after the path name, in the form of a dash ("\-") followed by an option +list. The option list is used for all subsequent exports on that line +only. +.PP +Blank lines are ignored. A pound sign ("#") introduces a comment to the +end of the line. Entries may be continued across newlines using a +backslash. If an export name contains spaces it should be quoted using +double quotes. You can also specify spaces or other unusual character in +the export name using a backslash followed by the character code as three +octal digits. +.PP +To apply changes to this file, run +.BR "exportfs \-ra" +or restart the NFS server. +.PP +.SS Machine Name Formats +NFS clients may be specified in a number of ways: +.IP "single host +You may specify a host either by an +abbreviated name recognized be the resolver, the fully qualified domain +name, an IPv4 address, or an IPv6 address. IPv6 addresses must not be +inside square brackets in /etc/exports lest they be confused with +character-class wildcard matches. +.IP "IP networks +You can also export directories to all hosts on an IP (sub-) network +simultaneously. This is done by specifying an IP address and netmask pair +as +.IR address/netmask +where the netmask can be specified in dotted-decimal format, or as a +contiguous mask length. +For example, either `/255.255.252.0' or `/22' appended +to the network base IPv4 address results in identical subnetworks with 10 bits +of host. IPv6 addresses must use a contiguous mask length and must not be inside square brackets to avoid confusion with character-class wildcards. Wildcard characters generally do not work on IP addresses, though they +may work by accident when reverse DNS lookups fail. +.IP "wildcards +Machine names may contain the wildcard characters \fI*\fR and \fI?\fR, or may contain character class lists within [square brackets]. +This can be used to make the \fIexports\fR file more compact; for instance, +\fI*.cs.foo.edu\fR matches all hosts in the domain +\fIcs.foo.edu\fR. As these characters also match the dots in a domain +name, the given pattern will also match all hosts within any subdomain +of \fIcs.foo.edu\fR. +.IP "netgroups +NIS netgroups may be given as +.IR @group . +Only the host part of each +netgroup members is consider in checking for membership. Empty host +parts or those containing a single dash (\-) are ignored. +.IP "anonymous +This is specified by a single +.I * +character (not to be confused with the +.I wildcard +entry above) and will match all clients. +.\".TP +.\".B =public +.\"This is a special ``hostname'' that identifies the given directory name +.\"as the public root directory (see the section on WebNFS in +.\".BR nfsd (8) +.\"for a discussion of WebNFS and the public root handle). When using this +.\"convention, +.\".B =public +.\"must be the only entry on this line, and must have no export options +.\"associated with it. Note that this does +.\".I not +.\"actually export the named directory; you still have to set the exports +.\"options in a separate entry. +.\".PP +.\"The public root path can also be specified by invoking +.\".I nfsd +.\"with the +.\".B \-\-public\-root +.\"option. Multiple specifications of a public root will be ignored. +.PP +If a client matches more than one of the specifications above, then +the first match from the above list order takes precedence - regardless of +the order they appear on the export line. However, if a client matches +more than one of the same type of specification (e.g. two netgroups), +then the first match from the order they appear on the export line takes +precedence. +.SS RPCSEC_GSS security +You may use the special strings "gss/krb5", "gss/krb5i", or "gss/krb5p" +to restrict access to clients using rpcsec_gss security. However, this +syntax is deprecated; on linux kernels since 2.6.23, you should instead +use the "sec=" export option: +.TP +.IR sec= +The sec= option, followed by a colon-delimited list of security flavors, +restricts the export to clients using those flavors. Available security +flavors include sys (the default--no cryptographic security), krb5 +(authentication only), krb5i (integrity protection), and krb5p (privacy +protection). For the purposes of security flavor negotiation, order +counts: preferred flavors should be listed first. The order of the sec= +option with respect to the other options does not matter, unless you +want some options to be enforced differently depending on flavor. +In that case you may include multiple sec= options, and following options +will be enforced only for access using flavors listed in the immediately +preceding sec= option. The only options that are permitted to vary in +this way are ro, rw, no_root_squash, root_squash, and all_squash. +.SS Transport layer security +The Linux NFS server allows the use of RPC-with-TLS (RFC 9289) to +protect RPC traffic between itself and its clients. +Alternately, administrators can secure NFS traffic using a VPN, +or an ssh tunnel or similar mechanism, in a way that is transparent +to the server. +.PP +To enable the use of RPC-with-TLS, the server's administrator must +install and configure +.BR tlshd +to handle transport layer security handshake requests from the local +kernel. +Clients can then choose to use RPC-with-TLS or they may continue +operating without it. +.PP +Administrators may require the use of RPC-with-TLS to protect access +to individual exports. +This is particularly useful when using non-cryptographic security +flavors such as +.IR sec=sys . +The +.I xprtsec= +option, followed by an unordered colon-delimited list of security policies, +can restrict access to the export to only clients that have negotiated +transport-layer security. +Currently supported transport layer security policies include: +.TP +.IR none +The server permits clients to access the export +without the use of transport layer security. +.TP +.IR tls +The server permits clients that have negotiated an RPC-with-TLS session +without peer authentication (confidentiality only) to access the export. +Clients are not required to offer an x.509 certificate +when establishing a transport layer security session. +.TP +.IR mtls +The server permits clients that have negotiated an RPC-with-TLS session +with peer authentication to access the export. +The server requires clients to offer an x.509 certificate +when establishing a transport layer security session. +.PP +If RPC-with-TLS is configured and enabled and the +.I xprtsec= +option is not specified, the default setting for an export is +.IR xprtsec=none:tls:mtls . +With this setting, the server permits clients to use any transport +layer security mechanism or none at all to access the export. +.SS General Options +.BR exportfs +understands the following export options: +.TP +.IR secure +This option requires that requests not using gss originate on an +Internet port less than IPPORT_RESERVED (1024). This option is on by default. +To turn it off, specify +.IR insecure . +(NOTE: older kernels (before upstream kernel version 4.17) enforced this +requirement on gss requests as well.) +.TP +.IR rw +Allow both read and write requests on this NFS volume. The +default is to disallow any request which changes the filesystem. +This can also be made explicit by using +the +.IR ro " option. +.TP +.IR async +This option allows the NFS server to violate the NFS protocol and +reply to requests before any changes made by that request have been +committed to stable storage (e.g. disc drive). + +Using this option usually improves performance, but at the cost that +an unclean server restart (i.e. a crash) can cause data to be lost or +corrupted. + +.TP +.IR sync +Reply to requests only after the changes have been committed to stable +storage (see +.IR async +above). + +In releases of nfs-utils up to and including 1.0.0, the +.I async +option was the +default. In all releases after 1.0.0, +.I sync +is the default, and +.I async +must be explicitly requested if needed. +.TP +.IR no_wdelay +This option has no effect if +.I async +is also set. The NFS server will normally delay committing a write request +to disc slightly if it suspects that another related write request may be in +progress or may arrive soon. This allows multiple write requests to +be committed to disc with the one operation which can improve +performance. If an NFS server received mainly small unrelated +requests, this behaviour could actually reduce performance, so +.IR no_wdelay +is available to turn it off. +The default can be explicitly requested with the +.IR wdelay " option. +.TP +.IR nohide +This option is based on the option of the same name provided in IRIX +NFS. Normally, if a server exports two filesystems one of which is +mounted on the other, then the client will have to mount both +filesystems explicitly to get access to them. If it just mounts the +parent, it will see an empty directory at the place where the other +filesystem is mounted. That filesystem is "hidden". + +Setting the +.I nohide +option on a filesystem causes it not to be hidden, and an +appropriately authorised client will be able to move from the parent to +that filesystem without noticing the change. + +However, some NFS clients do not cope well with this situation as, for +instance, it is then possible for two files in the one apparent +filesystem to have the same inode number. + +The +.I nohide +option is currently only effective on +.I "single host +exports. It does not work reliably with netgroup, subnet, or wildcard +exports. + +This option can be very useful in some situations, but it should be +used with due care, and only after confirming that the client system +copes with the situation effectively. + +The option can be explicitly disabled for NFSv2 and NFSv3 with +.IR hide . + +This option is not relevant when NFSv4 is use. NFSv4 never hides +subordinate filesystems. Any filesystem that is exported will be +visible where expected when using NFSv4. +.TP +.I crossmnt +This option is similar to +.I nohide +but it makes it possible for clients to access all filesystems mounted +on a filesystem marked with +.IR crossmnt . +Thus when a child filesystem "B" is mounted on a parent "A", setting +crossmnt on "A" has a similar effect to setting "nohide" on B. + +With +.I nohide +the child filesystem needs to be explicitly exported. With +.I crossmnt +it need not. If a child of a +.I crossmnt +file is not explicitly exported, then it will be implicitly exported +with the same export options as the parent, except for +.IR fsid= . +This makes it impossible to +.B not +export a child of a +.I crossmnt +filesystem. If some but not all subordinate filesystems of a parent +are to be exported, then they must be explicitly exported and the +parent should not have +.I crossmnt +set. + +The +.I nocrossmnt +option can explictly disable +.I crossmnt +if it was previously set. This is rarely useful. +.TP +.IR no_subtree_check +This option disables subtree checking, which has mild security +implications, but can improve reliability in some circumstances. + +If a subdirectory of a filesystem is exported, but the whole +filesystem isn't then whenever a NFS request arrives, the server must +check not only that the accessed file is in the appropriate filesystem +(which is easy) but also that it is in the exported tree (which is +harder). This check is called the +.IR subtree_check . + +In order to perform this check, the server must include some +information about the location of the file in the "filehandle" that is +given to the client. This can cause problems with accessing files that +are renamed while a client has them open (though in many simple cases +it will still work). + +subtree checking is also used to make sure that files inside +directories to which only root has access can only be accessed if the +filesystem is exported with +.I no_root_squash +(see below), even if the file itself allows more general access. + +As a general guide, a home directory filesystem, which is normally +exported at the root and may see lots of file renames, should be +exported with subtree checking disabled. A filesystem which is mostly +readonly, and at least doesn't see many file renames (e.g. /usr or +/var) and for which subdirectories may be exported, should probably be +exported with subtree checks enabled. + +The default of having subtree checks enabled, can be explicitly +requested with +.IR subtree_check . + +From release 1.1.0 of nfs-utils onwards, the default will be +.I no_subtree_check +as subtree_checking tends to cause more problems than it is worth. +If you genuinely require subtree checking, you should explicitly put +that option in the +.B exports +file. If you put neither option, +.B exportfs +will warn you that the change is pending. + +.TP +.IR insecure_locks +.TP +.IR no_auth_nlm +This option (the two names are synonymous) tells the NFS server not to require authentication of +locking requests (i.e. requests which use the NLM protocol). Normally +the NFS server will require a lock request to hold a credential for a +user who has read access to the file. With this flag no access checks +will be performed. + +Early NFS client implementations did not send credentials with lock +requests, and many current NFS clients still exist which are based on +the old implementations. Use this flag if you find that you can only +lock files which are world readable. + +The default behaviour of requiring authentication for NLM requests can +be explicitly requested with either of the synonymous +.IR auth_nlm , +or +.IR secure_locks . +.\".TP +.\".I noaccess +.\"This makes everything below the directory inaccessible for the named +.\"client. This is useful when you want to export a directory hierarchy to +.\"a client, but exclude certain subdirectories. The client's view of a +.\"directory flagged with noaccess is very limited; it is allowed to read +.\"its attributes, and lookup `.' and `..'. These are also the only entries +.\"returned by a readdir. +.\".TP +.\".IR link_relative +.\"Convert absolute symbolic links (where the link contents start with a +.\"slash) into relative links by prepending the necessary number of ../'s +.\"to get from the directory containing the link to the root on the +.\"server. This has subtle, perhaps questionable, semantics when the file +.\"hierarchy is not mounted at its root. +.\".TP +.\".IR link_absolute +.\"Leave all symbolic link as they are. This is the default operation. + +.TP +.IR mountpoint= path +.TP +.I mp +This option makes it possible to only export a directory if it has +successfully been mounted. +If no path is given (e.g. +.IR mountpoint " or " mp ) +then the export point must also be a mount point. If it isn't then +the export point is not exported. This allows you to be sure that the +directory underneath a mountpoint will never be exported by accident +if, for example, the filesystem failed to mount due to a disc error. + +If a path is given (e.g. +.IR mountpoint= "/path or " mp= /path) +then the nominated path must be a mountpoint for the exportpoint to be +exported. + +.TP +.IR fsid= num|root|uuid +NFS needs to be able to identify each filesystem that it exports. +Normally it will use a UUID for the filesystem (if the filesystem has +such a thing) or the device number of the device holding the +filesystem (if the filesystem is stored on the device). + +As not all filesystems are stored on devices, and not all filesystems +have UUIDs, it is sometimes necessary to explicitly tell NFS how to +identify a filesystem. This is done with the +.I fsid= +option. + +For NFSv4, there is a distinguished filesystem which is the root of +all exported filesystem. This is specified with +.I fsid=root +or +.I fsid=0 +both of which mean exactly the same thing. + +Other filesystems can be identified with a small integer, or a UUID +which should contain 32 hex digits and arbitrary punctuation. + +Linux kernels version 2.6.20 and earlier do not understand the UUID +setting so a small integer must be used if an fsid option needs to be +set for such kernels. Setting both a small number and a UUID is +supported so the same configuration can be made to work on old and new +kernels alike. + +.TP +.IR nordirplus +This option will disable READDIRPLUS request handling. When set, +READDIRPLUS requests from NFS clients return NFS3ERR_NOTSUPP, and +clients fall back on READDIR. This option affects only NFSv3 clients. +.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.) + +.TP +.IR pnfs +This option enables the use of the pNFS extension if the protocol level +is NFSv4.1 or higher, and the filesystem supports pNFS exports. With +pNFS clients can bypass the server and perform I/O directly to storage +devices. The default can be explicitly requested with the +.I no_pnfs +option. + +.TP +.IR security_label +With this option set, clients using NFSv4.2 or higher will be able to +set and retrieve security labels (such as those used by SELinux). This +will only work if all clients use a consistent security policy. Note +that early kernels did not support this export option, and instead +enabled security labels by default. + +.TP +.IR reexport= auto-fsidnum|predefined-fsidnum +This option helps when a NFS share is re-exported. Since the NFS server +needs a unique identifier for each exported filesystem and a NFS share +cannot provide such, usually a manual fsid is needed. +As soon +.IR crossmnt +is used manually assigning fsid won't work anymore. This is where this +option becomes handy. It will automatically assign a numerical fsid +to exported NFS shares. The fsid and path relations are stored in a SQLite +database. If +.IR auto-fsidnum +is selected, the fsid is also autmatically allocated. +.IR predefined-fsidnum +assumes pre-allocated fsid numbers and will just look them up. +This option depends also on the kernel, you will need at least kernel version +5.19. +Since +.IR reexport= +can automatically allocate and assign numerical fsids, it is no longer possible +to have numerical fsids in other exports as soon this option is used in at least +one export entry. + +The association between fsid numbers and paths is stored in a SQLite database. +Don't edit or remove the database unless you know exactly what you're doing. +.IR predefined-fsidnum +is useful when you have used +.IR auto-fsidnum +before and don't want further entries stored. + + +.SS User ID Mapping +.PP +.B nfsd +bases its access control to files on the server machine on the uid and +gid provided in each NFS RPC request. The normal behavior a user would +expect is that she can access her files on the server just as she would +on a normal file system. This requires that the same uids and gids are +used on the client and the server machine. This is not always true, nor +is it always desirable. +.PP +Very often, it is not desirable that the root user on a client machine +is also treated as root when accessing files on the NFS server. To this +end, uid 0 is normally mapped to a different id: the so-called +anonymous or +.I nobody +uid. This mode of operation (called `root squashing') is the default, +and can be turned off with +.IR no_root_squash . +.PP +By default, +.\".B nfsd +.\"tries to obtain the anonymous uid and gid by looking up user +.\".I nobody +.\"in the password file at startup time. If it isn't found, a uid and gid +.B exportfs +chooses a uid and gid +of 65534 for squashed access. These values can also be overridden by +the +.IR anonuid " and " anongid +options. +.\".PP +.\"In addition to this, +.\".B nfsd +.\"lets you specify arbitrary uids and gids that should be mapped to user +.\"nobody as well. +Finally, you can map all user requests to the +anonymous uid by specifying the +.IR all_squash " option. +.PP +Here's the complete list of mapping options: +.TP +.IR root_squash +Map requests from uid/gid 0 to the anonymous uid/gid. Note that this does +not apply to any other uids or gids that might be equally sensitive, such as +user +.IR bin +or group +.IR staff . +.TP +.IR no_root_squash +Turn off root squashing. This option is mainly useful for diskless clients. +.TP +.IR all_squash +Map all uids and gids to the anonymous user. Useful for NFS-exported +public FTP directories, news spool directories, etc. The opposite option +is +.IR no_all_squash , +which is the default setting. +.TP +.IR anonuid " and " anongid +These options explicitly set the uid and gid of the anonymous account. +This option is primarily useful for PC/NFS clients, where you might want +all requests appear to be from one user. As an example, consider the +export entry for +.B /home/joe +in the example section below, which maps all requests to uid 150 (which +is supposedly that of user joe). + +.SS Subdirectory Exports + +Normally you should only export only the root of a filesystem. The NFS +server will also allow you to export a subdirectory of a filesystem, +however, this has drawbacks: + +First, it may be possible for a malicious user to access files on the +filesystem outside of the exported subdirectory, by guessing filehandles +for those other files. The only way to prevent this is by using the +.IR no_subtree_check +option, which can cause other problems. + +Second, export options may not be enforced in the way that you would +expect. For example, the +.IR security_label +option will not work on subdirectory exports, and if nested subdirectory +exports change the +.IR security_label +or +.IR sec= +options, NFSv4 clients will normally see only the options on the parent +export. Also, where security options differ, a malicious client may use +filehandle-guessing attacks to access the files from one subdirectory +using the options from another. + + +.SS Extra Export Tables +After reading +.I /etc/exports +.B exportfs +reads files in the +.I /etc/exports.d +directory as extra export tables. Only files ending in +.I .exports +are considered. Files beginning with a dot are ignored. +The format for extra export tables is the same as +.I /etc/exports +. +.IP +.SH EXAMPLE +.PP +.nf +.ta +3i +# sample /etc/exports file +/ master(rw) trusty(rw,no_root_squash) +/projects proj*.local.domain(rw) +/usr *.local.domain(ro) @trusted(rw) +/home/joe pc001(rw,all_squash,anonuid=150,anongid=100) +/pub *(ro,insecure,all_squash) +/srv/www \-sync,rw server @trusted @external(ro) +/foo 2001:db8:9:e54::/64(rw) 192.0.2.0/24(rw) +/build buildhost[0-9].local.domain(rw) +.\"/pub/private (noaccess) +.fi +.PP +The first line exports the entire filesystem to machines master and trusty. +In addition to write access, all uid squashing is turned off for host +trusty. The second and third entry show examples for wildcard hostnames +and netgroups (this is the entry `@trusted'). The fourth line shows the +entry for the PC/NFS client discussed above. Line 5 exports the +public FTP directory to every host in the world, executing all requests +under the nobody account. The +.I insecure +option in this entry also allows clients with NFS implementations that +don't use a reserved port for NFS. +The sixth line exports a directory read-write to the machine 'server' +as well as the `@trusted' netgroup, and read-only to netgroup `@external', +all three mounts with the `sync' option enabled. The seventh line exports +a directory to both an IPv6 and an IPv4 subnet. The eighth line demonstrates +a character class wildcard match. +.\" The last line denies all NFS clients +.\"access to the private directory. +.\".SH CAVEATS +.\"Unlike other NFS server implementations, this +.\".B nfsd +.\"allows you to export both a directory and a subdirectory thereof to +.\"the same host, for instance +.\".IR /usr " and " /usr/X11R6 . +.\"In this case, the mount options of the most specific entry apply. For +.\"instance, when a user on the client host accesses a file in +.\".IR /usr/X11R6 , +.\"the mount options given in the +.\".I /usr/X11R6 +.\"entry apply. This is also true when the latter is a wildcard or netgroup +.\"entry. +.SH FILES +/etc/exports +/etc/exports.d +.SH SEE ALSO +.BR exportfs (8), +.BR netgroup (5), +.BR mountd (8), +.BR nfsd (8), +.BR showmount (8), +.BR tlshd (8). +.\".SH DIAGNOSTICS +.\"An error parsing the file is reported using syslogd(8) as level NOTICE from +.\"a DAEMON whenever +.\".BR nfsd (8) +.\"or +.\".BR mountd (8) +.\"is started up. Any unknown +.\"host is reported at that time, but often not all hosts are not yet known +.\"to +.\".BR named (8) +.\"at boot time, thus as hosts are found they are reported +.\"with the same +.\".BR syslogd (8) +.\"parameters. diff --git a/utils/exportfs/nfsd.man b/utils/exportfs/nfsd.man new file mode 100644 index 0000000..514153f --- /dev/null +++ b/utils/exportfs/nfsd.man @@ -0,0 +1,214 @@ +.\" +.\" nfsd(7) - The nfsd filesystem +.\" +.\" Copyright (C) 2003 Neil Brown +.\" Licensed for public use under the terms of the FSF +.\" General Public License (GPL) version 2. +.TH nfsd 7 "3 July 2003" +.SH NAME +nfsd \- special filesystem for controlling Linux NFS server +.SH SYNPOSIS +.B "mount -t nfsd nfsd /proc/fs/nfsd" +.SH DESCRIPTION +The +.B nfsd +filesystem is a special filesystem which provides access to the Linux +NFS server. Writing to files in this filesystem can affect the server. +Reading from them can provide information about the server. +.P +As well as this filesystem, there are a collection of files in the +.B procfs +filesystem (normally mounted at +.BR /proc ) +which are used to control the NFS server. +This manual page describes all of these files. +.P +The +.I exportfs +and +.I mountd +programs (part of the nfs-utils package) expect to find this +filesystem mounted at +.B /proc/fs/nfsd +or +.BR /proc/fs/nfs . +.SH DETAILS +Files in the +.B nfsd +filesystem include: +.TP +.B exports +This file contains a list of filesystems that are currently exported +and clients that each filesystem is exported to, together with a list +of export options for that client/filesystem pair. This is similar +to the +.B /proc/fs/nfs/exports +file in 2.4. +One difference is that a client doesn't necessarily correspond to just +one host. It can respond to a large collection of hosts that are +being treated identically. + +Each line of the file contains a path name, a client name, and a +number of options in parentheses. Any space, tab, newline or +back-slash character in the path name or client name will be replaced +by a backslash followed by the octal ASCII code for that character. + +.TP +.B threads +This file represents the number of +.B nfsd +thread currently running. Reading it will show the number of +threads. Writing an ASCII decimal number will cause the number of +threads to be changed (increased or decreased as necessary) to achieve +that number. + +.TP +.B filehandle +This is a somewhat unusual file in that what is read from it depends +on what was just written to it. It provides a transactional interface +where a program can open the file, write a request, and read a +response. If two separate programs open, write, and read at the same +time, their requests will not be mixed up. + +The request written to +.B filehandle +should be a client name, a path name, and a number of bytes. This +should be followed by a newline, with white-space separating the +fields, and octal quoting of special characters. + +On writing this, the program will be able to read back a filehandle +for that path as exported to the given client. The filehandle's length +will be at most the number of bytes given. + +The filehandle will be represented in hex with a leading '\ex'. + +.TP +.B clients/ +This directory contains a subdirectory for each NFSv4 client. Each file +under that subdirectory gives some details about the client in YAML +format. In addition, writing "expire\\n" to the +.B ctl +file will force the server to immediately revoke all state held by that +client. + +.PP +The directory +.B /proc/net/rpc +in the +.B procfs +filesystem contains a number of files and directories. +The files contain statistics that can be display using the +.I nfsstat +program. +The directories contain information about various caches that the NFS +server maintains to keep track of access permissions that different +clients have for different filesystems. +The caches are: + +.TP +.B auth.unix.ip +This cache contains a mapping from IP address to the name of the +authentication domain that the ipaddress should be treated as part of. + +.TP +.B nfsd.export +This cache contains a mapping from directory and domain to export +options. + +.TP +.B nfsd.fh +This cache contains a mapping from domain and a filesystem identifier +to a directory. The filesystem identifier is stored in the +filehandles and consists of a number indicating the type of identifier +and a number of hex bytes indicating the content of the identifier. + +.PP +Each directory representing a cache can hold from 1 to 3 files. They +are: +.TP +.B flush +When a number of seconds since epoch (1 Jan 1970) is written to this +file, all entries in the cache that were last updated before that file +become invalidated and will be flushed out. Writing a time in the +future (in seconds since epoch) will flush +everything. This is the only file that will always be present. + +.TP +.B content +This file, if present, contains a textual representation of ever entry +in the cache, one per line. If an entry is still in the cache +(because it is actively being used) but has expired or is otherwise +invalid, it will be presented as a comment (with a leading hash +character). + +.TP +.B channel +This file, if present, acts a channel for request from the kernel-based +nfs server to be passed to a user-space program for handling. + +When the kernel needs some information which isn't in the cache, it +makes a line appear in the +.B channel +file giving the key for the information. A user-space program should +read this, find the answer, and write a line containing the key, an +expiry time, and the content. +For example the kernel might make +.ti +5 +nfsd 127.0.0.1 +.br +appear in the +.B auth.unix.ip/content +file. The user-space program might then write +.ti +5 +nfsd 127.0.0.1 1057206953 localhost +.br +to indicate that 127.0.0.1 should map to localhost, at least for now. + +If the program uses select(2) or poll(2) to discover if it can read +from the +.B channel +then it will never see and end-of-file but when all requests have been +answered, it will block until another request appears. + +.PP +In the +.B /proc +filesystem there are 4 files that can be used to enabled extra tracing +of nfsd and related code. They are: +.in +5 +.B /proc/sys/sunrpc/nfs_debug +.br +.B /proc/sys/sunrpc/nfsd_debug +.br +.B /proc/sys/sunrpc/nlm_debug +.br +.B /proc/sys/sunrpc/rpc_debug +.br +.in -5 +They control tracing for the NFS client, the NFS server, the Network +Lock Manager (lockd) and the underlying RPC layer respectively. +Decimal numbers can be read from or written to these files. Each +number represents a bit-pattern where bits that are set cause certain +classes of tracing to be enabled. Consult the kernel header files to +find out what number correspond to what tracing. + +.SH NOTES +This file system is only available in Linux 2.6 and later series +kernels (and in the later parts of the 2.5 development series leading +up to 2.6). This man page does not apply to 2.4 and earlier. +.P +Previously the nfsctl systemcall was used for communication between nfsd +and user utilities. That systemcall was removed in kernel version 3.1. +Older nfs-utils versions were able to fall back to nfsctl if necessary; +that was removed from nfs-utils 1.3.5. + +.SH SEE ALSO +.BR nfsd (8), +.BR rpc.nfsd (8), +.BR exports (5), +.BR nfsstat (8), +.BR mountd (8) +.BR exportfs (8). + +.SH AUTHOR +NeilBrown -- cgit v1.2.3