Skip to content

Commit

Permalink
Merge tag 'nfsd-5.16' of git://linux-nfs.org/~bfields/linux
Browse files Browse the repository at this point in the history
Pull nfsd updates from Bruce Fields:
 "A slow cycle for nfsd: mainly cleanup, including Neil's patch dropping
  support for a filehandle format deprecated 20 years ago, and further
  xdr-related cleanup from Chuck"

* tag 'nfsd-5.16' of git://linux-nfs.org/~bfields/linux: (26 commits)
  nfsd4: remove obselete comment
  nfsd: document server-to-server-copy parameters
  NFSD:fix boolreturn.cocci warning
  nfsd: update create verifier comment
  SUNRPC: Change return value type of .pc_encode
  SUNRPC: Replace the "__be32 *p" parameter to .pc_encode
  NFSD: Save location of NFSv4 COMPOUND status
  SUNRPC: Change return value type of .pc_decode
  SUNRPC: Replace the "__be32 *p" parameter to .pc_decode
  SUNRPC: De-duplicate .pc_release() call sites
  SUNRPC: Simplify the SVC dispatch code path
  SUNRPC: Capture value of xdr_buf::page_base
  SUNRPC: Add trace event when alloc_pages_bulk() makes no progress
  svcrdma: Split svcrmda_wc_{read,write} tracepoints
  svcrdma: Split the svcrdma_wc_send() tracepoint
  svcrdma: Split the svcrdma_wc_receive() tracepoint
  NFSD: Have legacy NFSD WRITE decoders use xdr_stream_subsegment()
  SUNRPC: xdr_stream_subsegment() must handle non-zero page_bases
  NFSD: Initialize pointer ni with NULL and not plain integer 0
  NFSD: simplify struct nfsfh
  ...
  • Loading branch information
torvalds committed Nov 11, 2021
2 parents 2ec20f4 + 80479eb commit 38764c7
Show file tree
Hide file tree
Showing 43 changed files with 1,155 additions and 1,050 deletions.
14 changes: 14 additions & 0 deletions Documentation/admin-guide/kernel-parameters.txt
Original file line number Diff line number Diff line change
Expand Up @@ -3253,13 +3253,27 @@
driver. A non-zero value sets the minimum interval
in seconds between layoutstats transmissions.

nfsd.inter_copy_offload_enable =
[NFSv4.2] When set to 1, the server will support
server-to-server copies for which this server is
the destination of the copy.

nfsd.nfsd4_ssc_umount_timeout =
[NFSv4.2] When used as the destination of a
server-to-server copy, knfsd temporarily mounts
the source server. It caches the mount in case
it will be needed again, and discards it if not
used for the number of milliseconds specified by
this parameter.

nfsd.nfs4_disable_idmapping=
[NFSv4] When set to the default of '1', the NFSv4
server will return only numeric uids and gids to
clients using auth_sys, and will accept numeric uids
and gids from such clients. This is intended to ease
migration from NFSv2/v3.


nmi_backtrace.backtrace_idle [KNL]
Dump stacks even of idle CPUs in response to an
NMI stack-backtrace request.
Expand Down
1 change: 1 addition & 0 deletions Documentation/filesystems/nfs/index.rst
Original file line number Diff line number Diff line change
Expand Up @@ -11,3 +11,4 @@ NFS
rpc-server-gss
nfs41-server
knfsd-stats
reexport
113 changes: 113 additions & 0 deletions Documentation/filesystems/nfs/reexport.rst
Original file line number Diff line number Diff line change
@@ -0,0 +1,113 @@
Reexporting NFS filesystems
===========================

Overview
--------

It is possible to reexport an NFS filesystem over NFS. However, this
feature comes with a number of limitations. Before trying it, we
recommend some careful research to determine whether it will work for
your purposes.

A discussion of current known limitations follows.

"fsid=" required, crossmnt broken
---------------------------------

We require the "fsid=" export option on any reexport of an NFS
filesystem. You can use "uuidgen -r" to generate a unique argument.

The "crossmnt" export does not propagate "fsid=", so it will not allow
traversing into further nfs filesystems; if you wish to export nfs
filesystems mounted under the exported filesystem, you'll need to export
them explicitly, assigning each its own unique "fsid= option.

Reboot recovery
---------------

The NFS protocol's normal reboot recovery mechanisms don't work for the
case when the reexport server reboots. Clients will lose any locks
they held before the reboot, and further IO will result in errors.
Closing and reopening files should clear the errors.

Filehandle limits
-----------------

If the original server uses an X byte filehandle for a given object, the
reexport server's filehandle for the reexported object will be X+22
bytes, rounded up to the nearest multiple of four bytes.

The result must fit into the RFC-mandated filehandle size limits:

+-------+-----------+
| NFSv2 | 32 bytes |
+-------+-----------+
| NFSv3 | 64 bytes |
+-------+-----------+
| NFSv4 | 128 bytes |
+-------+-----------+

So, for example, you will only be able to reexport a filesystem over
NFSv2 if the original server gives you filehandles that fit in 10
bytes--which is unlikely.

In general there's no way to know the maximum filehandle size given out
by an NFS server without asking the server vendor.

But the following table gives a few examples. The first column is the
typical length of the filehandle from a Linux server exporting the given
filesystem, the second is the length after that nfs export is reexported
by another Linux host:

+--------+-------------------+----------------+
| | filehandle length | after reexport |
+========+===================+================+
| ext4: | 28 bytes | 52 bytes |
+--------+-------------------+----------------+
| xfs: | 32 bytes | 56 bytes |
+--------+-------------------+----------------+
| btrfs: | 40 bytes | 64 bytes |
+--------+-------------------+----------------+

All will therefore fit in an NFSv3 or NFSv4 filehandle after reexport,
but none are reexportable over NFSv2.

Linux server filehandles are a bit more complicated than this, though;
for example:

- The (non-default) "subtreecheck" export option generally
requires another 4 to 8 bytes in the filehandle.
- If you export a subdirectory of a filesystem (instead of
exporting the filesystem root), that also usually adds 4 to 8
bytes.
- If you export over NFSv2, knfsd usually uses a shorter
filesystem identifier that saves 8 bytes.
- The root directory of an export uses a filehandle that is
shorter.

As you can see, the 128-byte NFSv4 filehandle is large enough that
you're unlikely to have trouble using NFSv4 to reexport any filesystem
exported from a Linux server. In general, if the original server is
something that also supports NFSv3, you're *probably* OK. Re-exporting
over NFSv3 may be dicier, and reexporting over NFSv2 will probably
never work.

For more details of Linux filehandle structure, the best reference is
the source code and comments; see in particular:

- include/linux/exportfs.h:enum fid_type
- include/uapi/linux/nfsd/nfsfh.h:struct nfs_fhbase_new
- fs/nfsd/nfsfh.c:set_version_and_fsid_type
- fs/nfs/export.c:nfs_encode_fh

Open DENY bits ignored
----------------------

NFS since NFSv4 supports ALLOW and DENY bits taken from Windows, which
allow you, for example, to open a file in a mode which forbids other
read opens or write opens. The Linux client doesn't use them, and the
server's support has always been incomplete: they are enforced only
against other NFS users, not against processes accessing the exported
filesystem locally. A reexport server will also not pass them along to
the original server, so they will not be enforced between clients of
different reexport servers.
6 changes: 2 additions & 4 deletions fs/lockd/svc.c
Original file line number Diff line number Diff line change
Expand Up @@ -780,11 +780,9 @@ module_exit(exit_nlm);
static int nlmsvc_dispatch(struct svc_rqst *rqstp, __be32 *statp)
{
const struct svc_procedure *procp = rqstp->rq_procinfo;
struct kvec *argv = rqstp->rq_arg.head;
struct kvec *resv = rqstp->rq_res.head;

svcxdr_init_decode(rqstp);
if (!procp->pc_decode(rqstp, argv->iov_base))
if (!procp->pc_decode(rqstp, &rqstp->rq_arg_stream))
goto out_decode_err;

*statp = procp->pc_func(rqstp);
Expand All @@ -794,7 +792,7 @@ static int nlmsvc_dispatch(struct svc_rqst *rqstp, __be32 *statp)
return 1;

svcxdr_init_encode(rqstp);
if (!procp->pc_encode(rqstp, resv->iov_base + resv->iov_len))
if (!procp->pc_encode(rqstp, &rqstp->rq_res_stream))
goto out_encode_err;

return 1;
Expand Down
Loading

0 comments on commit 38764c7

Please sign in to comment.