【问题标题】:Writing to a remote file: When does write() really return?写入远程文件:write() 何时真正返回?
【发布时间】:2011-12-04 07:23:39
【问题描述】:

我有一个客户端节点将文件写入另一个节点上的硬盘(实际上我正在写入并行 fs)。

我想了解的是:
当我write()(或pwrite())时,write 调用究竟何时返回?

我看到了三种可能性:

  1. write 在客户端对 I/O 操作进行排队后立即返回:
    在这种情况下,write 可以在数据实际离开客户端节点之前返回(如果您正在写入本地硬盘驱动器,则写入调用采用延迟写入,其中数据只是排队等待写入。但这是否也会发生当您写入远程硬盘时?)。我写了一个测试用例,在其中我将一个大矩阵(1GByte)写入文件。没有fsync,它显示出非常高的带宽值,而使用fsync,结果看起来更真实。所以看起来它可能正在使用延迟写入。

  2. write 在数据传输到服务器缓冲区后返回:
    现在数据在服务器上,但驻留在其主存储器的缓冲区中,但尚未永久存储在硬盘驱动器上。在这种情况下,I/O 时间应该以通过网络传输数据的时间为主。

  3. write 在数据实际存储到硬盘后返回:
    我敢肯定,默认情况下不会发生这种情况(除非您编写的文件非常大,这会导致您的 RAM 被填满并最终被清除等等......)。

另外,我想确定的是:
是否会出现程序在没有任何数据实际离开客户端节点的情况下终止的情况,这样延迟、带宽和硬盘驱动器带宽等网络参数根本不包含在程序的执行时间中?考虑到我们不做fsync 或类似的事情。

编辑:我正在使用 pvfs2 并行文件系统

【问题讨论】:

  • 哪个网络文件系统?规则在文件系统中,系统管理员可以在 1、2 和 3 之间进行选择。
  • 我正在写入 pvfs2 并行文件系统

标签: linux file-io io


【解决方案1】:

选项 3. 当然简单且安全。然而,一个生产质量的 POSIX 兼容并行文件系统,其性能足以让任何人真正关心使用它,通常会使用选项 1 结合一些或多或少涉及的机制来避免冲突,例如多个客户端缓存同一个文件。

俗话说,“计算机科学中只有两件难事:缓存失效和命名事物以及非一错误”。

如果文件系统应该与 POSIX 兼容,您需要去学习 POSIX fs 语义,并查看 fs 如何在获得良好性能的同时支持这些语义(或者,它跳过了 POSIX 语义的哪些部分,例如 NFS) .使这个错误的有趣之处在于,POSIX fs 语义可以追溯到 1970 年代,几乎没有考虑如何支持网络文件系统。

我不具体了解 pvfs2,但通常为了符合 POSIX 并提供良好的性能,选项 1 可以与某种缓存一致性协议(例如 Lustre 使用)一起使用。对于 fsync(),数据必须在 fsync() 返回之前实际传输到服务器并提交到服务器上的稳定存储(磁盘或电池支持的写入缓存)。当然,客户端对脏页的数量有一定的限制,之后它将阻止进一步的 write() 到文件,直到一些已经传输到服务器。

【讨论】:

    【解决方案2】:

    您可以选择三个选项中的任何一个。这取决于您提供给open 调用的标志。这取决于本地安装文件系统的方式。这也取决于远程服务器的配置方式。

    以下内容均取自 Linux。 Solaris 和其他可能有所不同。

    一些重要的open 标志是O_SYNCO_DIRECTO_DSYNCO_RSYNC

    一些重要的 NFS 挂载标志是 acnoacctonoctolookupcachesyncasync

    用于导出 NFS 的一些重要标志是 syncasyncno_wdelay。当然,NFS 正在导出的文件系统的挂载标志也很重要。例如,如果您从 Linux 导出 XFS 或 EXT4,并且出于某种原因使用了nobarrier 标志,则服务器端断电几乎肯定会导致数据丢失。

    【讨论】:

    • 假设我使用 O_RDWR(而不是任何 SYNC 或 O_DIRECT 标志)打开文件。在这种情况下会发生什么?
    • @KVM:这取决于系统设置,但我想他们会使用包括缓存在内的最佳设置。在没有特殊标志的情况下,数据将缓存在客户端和服务器端的 RAM 中。它将在时间允许的情况下刷新到磁盘。
    • 同意,但是当数据仍然驻留在客户端时程序可以终止吗?或者 write() 只有在数据至少存储在服务器缓冲区后才会返回?
    • 操作系统缓存独立于正在运行的程序。程序可以退出,并且它写入的所有内容都将保留在缓存中,直到它被写入磁盘。检查close()的返回值通常是明智的,因为那里会报告错误。
    • @KVM:至于这一切如何适用于 PVFSv2,我不完全确定。我假设您已经阅读了 PVFS 文档。我扫描了它,但我没有看到任何关于缓存和不缓存的保证。您可能需要阅读其 Linux 内核模块的源代码。
    猜你喜欢
    • 1970-01-01
    • 2013-01-06
    • 2015-01-15
    • 1970-01-01
    • 2016-02-19
    • 2016-01-06
    • 1970-01-01
    • 2020-12-21
    • 1970-01-01
    相关资源
    最近更新 更多