我们有一个虚拟服务器,它有一个 NFS 共享,其他服务器会向其写入数据。今天,NFS 共享变得无法访问。系统日志中充满了类似这样的消息:
RPC: fragment too large: 311176
我在 Google 上搜索过,但找不到太多相关信息。有人能解释一下这是什么意思吗?
答案1
rpc 消息(NFS 是基于 rpc 的服务)可以拆分成多个帧(块)。任何 RPC 服务器都有帧大小限制以及消息大小限制。“RPC:片段太大:”表示 NFS 服务器收到的 rpc 帧大于最大允许大小。此消息可能指向客户端代码、服务器代码中的错误或网络问题。端口扫描也可能触发这种情况。
答案2
在红帽中
https://access.redhat.com/solutions/2065483
RHEL NFS 服务器的默认最大 rsize/wsize 通常在 NFS 服务器启动时计算,并且基于系统的内存量。内存越多,允许的值越大,最高可达 1048576。
如果 NFS 服务器选择在 NFS 客户端挂载共享时降低此值,则可能会出现问题。如果 NFS 服务器以较少的内存重新启动,则可能会出现这种情况。根据内存量的变化,NFS 服务器可能会选择较小的 rsize/wsize 最大值。
但是,在 NFS 服务器重新启动之前已经挂载了 NFS 共享的 NFS 客户端将不知道允许的最大 rsize/wsize 已更改。当 NFS 客户端挂载 NFS 共享时,将向其传达允许的最大值。NFS 客户端仍将认为允许使用旧的较大尺寸发送 RPC。但是,大型 RPC 会被 NFS 服务器拒绝和丢弃,并生成 RPC:fragment too large 以达到新的最大值。
在 NFS 源代码中
https://docs.huihoo.com/doxygen/linux/kernel/3.7/nfs__xdr_8h_source.html
要更改 NFS 客户端支持的最大 rsize 和 wsize,请调整 NFS_MAX_FILE_IO_SIZE。64KB 是典型的最大值,但某些服务器可以支持 1 兆字节或更多。默认值为 4096 字节,这对于 NFS over UDP 来说是合理的。
#define NFS_MAX_FILE_IO_SIZE (1048576U)
#define NFS_DEF_FILE_IO_SIZE (4096U)
#define NFS_MIN_FILE_IO_SIZE (1024U)
答案3
我在 Ubuntu Xenial NFS 服务器上看到了这个问题,在我将其 RAM 从 8gb 调整为 4gb 后触发了这个问题。
最初从服务器挂载了 NFS 共享的客户端(大概)已经自动协商了如下挂载方式(运行的输出mount
):
nfs-server:/backups/something on /backup type nfs4 (rw,noatime,vers=4.2,rsize=1048576,wsize=1048576,namlen=255,hard,proto=tcp,timeo=600,retrans=2,sec=sys,clientaddr=10.1.1.2,local_lock=none,addr=10.1.1.1)
解决方法是重新启动客户端,或者仅卸载/挂载文件系统,此时它将协商的 rsize/wsize 更改为如下形式:
nfs-server:/backups/something on /backup type nfs4 (rw,noatime,vers=4.2,rsize=524288,wsize=524288,namlen=255,hard,proto=tcp,timeo=600,retrans=2,sec=sys,clientaddr=10.1.1.2,local_lock=none,addr=10.1.1.1)
因此,我认为在 NFS 挂载上设置过大的 rsize/wsize 也可能会引发该问题。