同一服务器上的 NFS/CIFS 目录之间复制速度缓慢

同一服务器上的 NFS/CIFS 目录之间复制速度缓慢

请耐心等待,我知道这需要阅读很多内容。这个问题可能适用于其他人,所以如果有答案就太好了。我不得不放弃悬赏,因为它即将到期。

当我从客户端 (Ubuntu) 向 NFS 服务器 (Debian) 复制或从 NFS 服务器 (Debian) 复制时,速度会达到最大值。但是,当我在同一台服务器上的两个目录之间复制时,速度会在 < 30MB/秒到 100MB/秒以上之间波动。大多数情况下速度在 50MB/秒左右。

直接在 NFS 服务器(本地磁盘)上执行相同的复制,我获得 100-150 MB/秒,有时甚至更快。此 NFS 导出和从同一服务器上的同一目录导出的 CIFS 共享之间的文件复制同样很慢,并且在同一服务器上通过 CIFS 在两个目录之间进行的复制也很慢。iperf显示客户端和服务器之间的双向速度为 941Mb/940Mb。

我确保 NFS 在服务器上使用异步。我还禁用了 ZFS 数据集上的同步,并尝试删除 ZFS 缓存和日志设备。

我已经在 4x2TB 磁盘的非常快的 ZFS 条带镜像上进行了测试,并使用 SSD 作为日志和缓存设备。

NFS 服务器规格:

Debian 8.2 核心 4Ghz AMD-FX
32GB RAM
ZFS raid 10,SSD 缓存/日志
17GB ARC
4x2GB WD 红色驱动器
Intel 82574L NIC

测试客户端:

Ubuntu 15.04,Core2Quad 2.4Ghz
8GB RAM
SSD
Intel 82574L NIC

这是当前的设置方式。/pool2/Media是我一直在测试的份额。

/etc/fstab在客户端:

UUID=575701cc-53b1-450c-9981-e1adeaa283f0 /               ext4        errors=remount-ro,discard,noatime,user_xattr 0       1
UUID=16e505ad-ab7d-4c92-b414-c6a90078c400 none            swap    sw              0       0 
/dev/fd0        /media/floppy0  auto    rw,user,noauto,exec,utf8 0       0
tmpfs    /tmp    tmpfs   mode=1777       0       0


igor:/pool2/other     /other        nfs         soft,bg,nfsvers=4,intr,rsize=65536,wsize=65536,timeo=50,nolock
igor:/pool2/Media       /Media          nfs     soft,bg,nfsvers=4,intr,rsize=65536,wsize=65536,timeo=50,nolock,noac
igor:/pool2/home        /nfshome        nfs     soft,bg,nfsvers=4,intr,rsize=65536,wsize=65536,timeo=50,nolock

/etc/exports在服务器(igor)上:

#LAN
/pool2/home 192.168.1.0/24(rw,sync,no_subtree_check,no_root_squash)
/pool2/other 192.168.1.0/24(rw,sync,no_subtree_check,no_root_squash)
/pool2/Media 192.168.1.0/24(rw,async,no_subtree_check,no_root_squash)
/test 192.168.1.0/24(rw,async,no_subtree_check,no_root_squash)

#OpenVPN
/pool2/home 10.0.1.0/24(rw,sync,no_subtree_check,no_root_squash)
/pool2/other 10.0.1.0/24(rw,sync,no_subtree_check,no_root_squash)
/pool2/Media 10.0.1.0/24(rw,sync,no_subtree_check,no_root_squash)

zpool状态:

  pool: pool2
 state: ONLINE
  scan: scrub repaired 0 in 6h10m with 0 errors on Sat Oct  3 08:10:26 2015
config:

        NAME                                                 STATE     READ WRITE CKSUM
        pool2                                                ONLINE       0     0     0
          mirror-0                                           ONLINE       0     0     0
            ata-WDC_WD20EFRX-68AX9N0_WD-WMC300004469         ONLINE       0     0     0
            ata-WDC_WD20EFRX-68EUZN0_WD-WCC4MLK57MVX         ONLINE       0     0     0
          mirror-1                                           ONLINE       0     0     0
            ata-WDC_WD20EFRX-68AX9N0_WD-WCC1T0429536         ONLINE       0     0     0
            ata-WDC_WD20EFRX-68EUZN0_WD-WCC4M0VYKFCE         ONLINE       0     0     0
        logs
          ata-KINGSTON_SV300S37A120G_50026B7751153A9F-part1  ONLINE       0     0     0
        cache
          ata-KINGSTON_SV300S37A120G_50026B7751153A9F-part2  ONLINE       0     0     0

errors: No known data errors

  pool: pool3
 state: ONLINE
  scan: scrub repaired 0 in 3h13m with 0 errors on Sat Oct  3 05:13:33 2015
config:

        NAME                                        STATE     READ WRITE CKSUM
        pool3                                       ONLINE       0     0     0
          ata-WDC_WD40EFRX-68WT0N0_WD-WCC4E5PSCNYV  ONLINE       0     0     0

errors: No known data errors

/pool2 bonnie++ 服务器上:

版本 1.97 ------顺序输出------ --顺序输入- --随机-
并发 1 -每个 Chr- --块-- -重写- -每个 Chr- --块-- --查找--
机器大小 K/秒 %CP K/秒 %CP K/秒 %CP K/秒 %CP K/秒 %CP /秒 %CP
伊戈尔 63G 100 99 187367 44 97357 24 325 99 274882 27 367.1 27

粘合

我尝试了绑定和直接连接,balance-rr 绑定,我得到了 220MB/秒的读取速度和 117MB/秒的写入速度,以及 40-50MB/秒的复制速度。

iperf 与绑定

[ ID] 间隔传输带宽 Retr
[ 4] 0.00-10.00 秒 1.10 GBytes 942 Mbits/秒 707 发送方
[ 4] 0.00-10.00 秒 1.10 GBytes 941 Mbits/秒接收器
[ 6] 0.00-10.00 秒 1.06 GBytes 909 Mbits/秒 672 发送方
[ 6] 0.00-10.00 秒 1.06 GBytes 908 Mbits/秒接收器
[总计] 0.00-10.00 秒 2.15 GBytes 1.85 Gbits/秒 1379 发送方
[总计] 0.00-10.00 秒 2.15 GBytes 1.85 Gbits/秒接收器

Bonnie++ 通过 NFS 进行绑定

版本 1.97 ------顺序输出------ --顺序输入- --随机-
并发 1 -每个 Chr- --块-- -重写- -每个 Chr- --块-- --查找--
机器大小 K/秒 %CP K/秒 %CP K/秒 %CP K/秒 %CP K/秒 %CP /秒 %CP
雾度 16G 1442 99 192941 16 89157 15 3375 96 179716 13 6082 77

删除 SSD 缓存/日志后,通过 NFS 进行复制,iostat 显示以下内容

常温常压 0.80 0.00 67.60 214.00 8561.60 23689.60 229.06 1.36 4.80 14.77 1.64 1.90 53.60
平均数 0.80 0.00 54.60 214.20 7016.00 23689.60 228.46 1.37 5.14 17.41 2.01 2.15 57.76
sdc 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00
标准差 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00
平均价格指数 1.60 0.00 133.00 385.20 17011.20 45104.00 239.73 2.24 4.31 12.29 1.56 1.57 81.60
自发性密度函数 0.40 0.00 121.40 385.40 15387.20 45104.00 238.72 2.36 4.63 14.29 1.58 1.62 82.16
可持续发展目标 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00
md0 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00
同步数字 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00

颞叶多普勒频谱

我通过 NFS 导出了 tmpfs 并进行了文件复制 - 速度为 108MB/秒。从服务器本地来看,速度为 410MB/秒。

zvol 通过 NFS 挂载

速度在 < 50MB/秒到 > 180MB/秒之间波动,但平均约为 100MB/秒。这正是我想要的。这个 zvol 与我测试的池 (pool2) 相同。这确实让我认为这更像是 ZFS 数据集/缓存类型的问题。

原始磁盘读取测试

使用此命令

dd if=/dev/disk/by-id/ata-WDC_WD20EFRX-68AX9N0_WD-WMC300004469 of=/dev/null bs=1M count=2000

我所有 4 个磁盘的速度都是 146-148MB/秒

池中的磁盘使用速度缓慢且不均匀

感谢 ZFS 邮件列表中一位非常有帮助的人,我知道如何做才能更均匀地使用磁盘。

ZFS 优先选择镜像 1 的原因是它似乎是在镜像 0 已被填满相当多之后才添加的,现在 ZFS 正在尝试重新平衡填充级别。

如果你想摆脱它并且有一些时间:zfs 迭代地将池的数据集发送到其自身的新数据集,然后销毁源,重复此操作直到池重新平衡。

我已经修复了这个问题,现在所有磁盘上的数据都是一致的 这使得 NFS 上的复制速度达到 75MB/秒。本地复制速度达到 118MB/秒。

问题

我的问题。如果你能回答任何一个问题,我就会接受你的答案:

  1. 我的问题该如何解决?(通过 NFS 复制速度很慢,但不是本地复制)
  2. 如果您无法回答第 1 个问题,您能否在具有 Linux 上的 ZFS 的类似 NFS 服务器上尝试此操作并告诉我结果,以便我可以进行比较?
  3. 如果您无法回答问题 1 或问题 2,您是否可以在类似但非 ZFS 的 NFS 服务器上尝试进行相同的测试?

答案1

嗯...我确实注意到了一些问题,我想我找到了一两个确凿的证据。但是,首先我会问几个问题,并对你的可能答案做出假设。我会提供一些乍一看似乎无关紧要的数据,但我保证,这些数据值得一读。所以,请等待... :-)

  • 我假设通过 raid10,您共有四个驱动器,条带+冗余。
  • 并且,您正在使用 Linux 自动突袭(而不是硬件突袭控制器)。
  • 我还假设所有 SATA 端口都可以以全速双向独立传输,并且所有 SATA 端口的速度都一样快。也就是说,如果您有一个 SATA 适配器/控制器,它完全能够以额定速度运行与其连接的所有磁盘。
  • 我还假设您拥有最新的 SATA 规格驱动器 + 控制器。即 6.0Gb/s。即 600MB/秒。保守起见,我们假设我们得到一半,即 300MB/秒
  • 客户端到服务器的 NIC 受到限制(为 100MB/s),因此无法对驱动器施加足够的压力。
  • 为了比 NIC 更快,在执行 NFS 到 NFS 时,我假设您使用的是本地主机,这样您就可以超越 NIC 限制的速度(我认为您说过您进行了绑定以表明这不是问题)

问题 #1。您报告的即使是快速的本地到本地传输速率似乎也很低。有了这么快的磁盘,我预计传输速率会超过 150MB/s。我有一个 3 磁盘 raid0 系统,速度只有 3.0Gb/s [适配器受限],我可以获得 450 MB/s 的条带化速度。您的磁盘/控制器的速度是我的 2 倍,因此,我预计 [由于条带化] 您的本地到本地传输速率会达到 300MB/秒,而不仅仅是 150MB/秒。或者,甚至可能是 600MB/秒 [减去 FS 开销,为了便于讨论,可能会将其减半]

  • 从您的 zpool 信息中,我注意到您的磁盘配置是 Western Digital,并且它是:
镜像-0
  ATA-WDC_WD20EFRX-68AX9N0
  ata-WDC_WD20EFRX-68EUZN0
镜像-1
  ATA-WDC_WD20EFRX-68AX9N0
  ata-WDC_WD20EFRX-68EUZN0
  • 现在让我们将其与您的 iostat 信息进行比较。在所有测试的所有驱动器上都有 iostat 信息可能会很好,但我相信我可以根据您提供的信息来诊断问题
  • sdb 和 sdd 已达到最大值
  • 正如你所说,这是奇怪的.我期望全部驱动器在 raid10 中具有平衡的使用/统计。这是 [我的] 确凿证据。
  • 结合两者。容量达到最大容量的驱动器与容量未达到最大容量的驱动器的型号略有不同。我推测 zpool 顺序是 sda/sdb sdc/sdd [但可能相反]
  • sda/sdc 是 68AX9N0
  • sdb/sdd 为 68EUZN0

问题 #2。通过 Google 搜索 WD20EFRX + 68AX9N0 + 68EUZN0,我找到了此页面:http://forums.whirlpool.net.au/archive/2197640

看起来 68EUZN0 驱动器可以在大约 8 秒后停放其磁头,而另一个驱动器在这方面更为智能 [反之亦然]。

因此,考虑到 NFS 缓存 + FS 缓存 + SSD 缓存,底层驱动器可能会处于空闲状态并停止运行。我猜 NFS 的额外缓存层是导致其崩溃的原因。

您可以通过改变 FS 同步选项来测试这一点,也许同步比异步更好。另外,如果可以的话,我会在 SSD 缓存关闭的情况下重新运行测试。这样做的目的是确保停放不会不是发生并观察结果。

正如网页上所述,有些实用程序可以调整停车延迟间隔。如果这是选项,请务必彻底研究它。

更新:

您的问题可以视为通过存储转发(保证交付)网络的吞吐量问题。注意,我不是谈论 NIC 或同等级别。

假设 I/O 操作就像一个包含请求(例如读/写、buf_addr、buf_len)的数据包,该请求存储在结构中。此请求数据包/结构在各种缓存层之间传递:NFS、ZFS、设备驱动程序、SATA 控制器、硬盘。在每个点,您都有到达该层的时间,以及请求转发到下一层时的出发时间。

在此上下文中,实际发生传输时的实际磁盘传输速度类似于链接速度。大多数人在考虑磁盘时,只考虑传输速度,而不考虑传输实际启动的时间。

在网络路由器中,数据包到达后,即使出站链路畅通,它们也并不总是立即转发。根据路由器策略,路由器可能会延迟数据包一段时间,希望有更多数据包从其他来源(如果是 UDP,则从同一来源)到达,这样路由器就可以将较小的数据包聚合成一个较大的数据包,以便更有效地在出站链路上传输。

对于磁盘,此“延迟”可以通过给定 FS 层的缓存策略来表征。换句话说,如果请求在时间 T 到达某一层,则它可以在 T+n 离开/到达,而不是在 T+1 离开该层并在 T+1 到达下一层。FS 缓存层可能会这样做,以便它可以进行寻道顺序优化/排序。

您看到的行为与由于拥塞而减少窗口的 TCP 套接字非常相似。

我认为将测试分开很重要。现在,您正在进行读取和写入。而且,您不知道哪个是限制因素/瓶颈。我认为将测试分为读取或写入会很有帮助。一个不错的基准测试程序可能会这样做。我主张的是更复杂的版本[这些只是粗略的例子,而不是确切的论据]:

对于写入,时间 dd if=/dev/zero of=/whatever_file count=64g
对于读取,时间 dd if=/whatever of=/dev/null count=64g
选择 64GB 的原因是它是物理内存的 2 倍,并消除了块缓存的影响。在测试之间执行同步命令。

在本地 FS 上应用此操作并在 NFS 上重复。

另外,在 /dev/{sda,sdb,sdc,sdd} 上进行测试

在这些测试期间执行 iostat。

请注意,在物理原始磁盘上进行读取测试可以为您提供硬件实际运行速度的基准/最大值。原始设备读取速度应接近驱动器传输规格的最大能力。硬盘的预期写入速度应该相似。如果不是,为什么不呢?所有磁盘的测试速度都应大致相同。我在这里要解释的是为什么在之前的测试中只有两个磁盘达到最大值的原因。

计算一下,假设最大传输速度为 600MB/秒,32GB 的容量至少需要 50 秒才能填满/刷新。那么,停放超时设置为多少呢?

此外,您可以通过 mem= 启动参数减少内核允许的物理内存量来稍微改变一下。尝试使用 mem=8g 之类的参数来查看效果。还有一些 /proc 条目可以调整块层缓存刷新策略。

另外,我的文件系统是 ext4 并使用 noatime 挂载。您可能需要考虑zfs set atime=off ...

另外,查看系统日志。有时,驱动器会报告感知错误,系统会将其重新配置为使用较低的传输速度。

另外,查看驱动器的 SMART 数据。你发现有什么异常吗?给定驱动器上的软重试过多(例如)。

就像我说的,本地磁盘性能比我预期的要差很多。我认为在使用 NFS 处理整个系统之前,需要先解决这个问题。如果所有 raid 磁盘的利用率都均衡且在合理范围内,我就不会太担心这个问题。

我的系统 [也有 WDC 磁盘] 没有配置 NFS(我经常使用 rsync)。接下来的 1-2 天内我有一些紧急的事情要做。之后,我会有时间尝试一下 [我自己也很好奇]。

更新 #2:

很好地解决了 ZFS 不平衡问题。这有助于解释我的“问题 #1”。可能如果重新平衡操作以某种方式在延迟/时间方面混淆了 NFS,从而导致“TCP 窗口/退避”行为,那么也解释一下 NFS 的不稳定性——虽然概率不是很高,但仍然是一种可能性。

使用 rsync 测试不需要/不想使用 NFS。如果你可以 ssh 进入服务器,rsyncNFS 是多余的。使用 NFS,只需使用 cp 等。要执行 rsync,请通过 ssh 直接转到底层 ZFS。即使没有 NFS 挂载,这也可以工作[这是我使用的 rsync 配置]:

导出 RSYNC_SSH="/usr/bin/ssh"
导出 SSH_NOCOMPRESS=1
rsync /wherever1 服务器:/zfsmount/whatever
执行此 localhost 或 bonded 操作可能会使性能达到您的预期(不包括 ZFS 不平衡问题)。如果是这样,它显然将问题缩小到 NFS本身

我仔细阅读了 NFS 的一些内核源代码。从我所看到的一点点来看,我不喜欢我看到的关于及时性的内容。NFS 始于 80 年代,当时链接速度很慢,因此它 [仍然] 有很多代码试图节省 NIC 带宽。也就是说,只有在绝对必要时才“提交”操作。不一定是我们想要的。在我想象的网络路由器策略类比中,NFS 的缓存似乎是具有“T+n”延迟的缓存。

我建议尽一切可能禁用 NFS 的缓存,并让其尽快将其请求传递给 ZFS。让 ZFS 成为智能缓存,让 NFS 成为“哑管道”。NFS 缓存只能是通用的(例如,它甚至不知道后备存储是 RAID,也不知道它所安装的基础 FS 的特殊特性)。ZFS 对 RAID 及其组成磁盘有深入的了解。因此,ZFS 的缓存可以更智能地做出选择。

我想说尝试让 NFS 进行同步挂载——这可能会奏效。另外,我看到了一些关于 noatime 的信息,所以也打开该选项。可能还有其他 NFS 调整/挂载选项。希望如果 NFS 是常见的问题,可以重新配置它以使其运行良好。

另一方面,如果没有选项可以让 NFS 屈服,那么 rsync over ssh 是否是一种可行的替代方案?实际用例是什么?似乎您正在使用 NFS 作为需要高性能的大量传输的管道(而不是 [比如说] 仅作为用户主目录的自动挂载点)。这是否用于客户端备份到服务器等?

相关内容