我这里有一个非常奇怪的情况。我的电脑工作正常,至少在大多数情况下,但有一件事情我无法处理。当我尝试从我的 Pendrive 复制文件时,一切正常——我得到了 16-19M/s ,它运行得很好。但是当我尝试将某些内容复制到同一个 Pendrive 时,我的 PC 死机了。鼠标指针停止移动一两秒钟,然后移动一点,然后再次停止。例如,在 Amarok 中播放某些东西时,声音就像机关枪。速度从500K/s跃升到15M/s,平均8M/s。仅当我将某些内容复制到 Pendrive 时才会发生这种情况。当复制过程完成后,一切恢复正常。
我尝试了一切——其他的随身碟、前面板上的不同 USB 端口或后面的那些端口,我什至更改了主板(前面板)上的 USB 引脚,但无论我把 USB 记忆棒放在哪里,它总是一样的。我尝试了不同的文件系统 - fat32, ext4. 我的笔记本电脑上的 Windows 设备没有问题。它必须是我的 PC 或系统中的某些东西。我不知道该找什么。我在独立的 Openbox 中使用 Debian 测试。我的电脑有点旧——Pentium D 3GHz、1GiB 内存、1.5TB WD Green 磁盘。如果您有什么可以帮助我解决这个问题的东西,我会很高兴听到这个消息。
我不知道我还应该提供什么信息,但是如果您需要什么,尽管问,我会尽快更新这篇文章。
我试图在 ubuntu 13.04 live cd 上重现这个问题。我安装了我的加密分区 + 加密交换并将我的 Pendrive 连接到 USB 端口。接下来我尝试启动一些应用程序,现在我有大约 820MiB 的 RAM 和大约 400MiB 的 SWAP。复制没有问题,根本没有冻结,一切都应该如此。所以,看起来是系统的故障,但究竟在哪里?什么会导致这种奇怪的行为?
有没有办法告诉 Linux 内核只将一定比例的内存用于缓冲区缓存?我知道/proc/sys/vm/drop_caches可以用来临时清除缓存,但是否有任何永久设置可以防止它增长到超过主内存的 50%?
我想这样做的原因是,我有一台运行 Ceph OSD 的服务器,它不断地从磁盘提供数据,并设法在几个小时内用完整个物理内存作为缓冲区缓存。同时,我需要运行将分配大量(数十 GB)物理内存的应用程序。与流行的看法相反(请参阅关于几乎所有有关缓冲区缓存的问题的建议),通过丢弃干净的缓存条目来自动释放内存不是即时的:当缓冲区缓存已满时,启动我的应用程序可能需要长达一分钟的时间( *),而在清除缓存后(使用echo 3 > /proc/sys/vm/drop_caches),相同的应用程序几乎立即启动。
(*) 根据 Vtune 在一个名为pageblock_pfn_to_page. 这个功能似乎与查找大页面所需的内存压缩有关,这让我相信实际上是碎片化的问题。
在 Ubuntu 18.04 系统上执行大型磁盘映像操作时,我遇到了系统范围的延迟/滞后问题。这是系统规格:
处理器:英特尔酷睿 i7(任何内核都不会接近容量)
内存:12GB(永不接近容量)
系统盘:SSD(永不接近容量)
外部磁盘:USB 3.0 5400 和 7200RPM 旋转磁盘
这些大型磁盘映像操作基本上是:
nice ionice dd if=/dev/usbdisk1 of=/dev/usbdisk2
由于我的系统文件都不在任何 USB 磁盘上,理论上,这不应该引入太多延迟。但是我发现当我对多个 USB 磁盘进行映像时,系统就会开始爬行。为什么?我的理解是每个磁盘都有自己的IO队列,那这是怎么回事呢?我该如何补救?
另外,FWIW,我根本不在乎 USB 磁盘的成像速度,因此我认为可以减慢这些操作以促进系统平稳运行的解决方案。
我一直在测试 Linux 4.18.16-200.fc28.x86_64。根据free -h.
我有vm.dirty*sysctl 的默认值。 dirty_background_ratio是 10,现在dirty_ratio是 20。根据我读过的所有内容,我希望 Linux 在达到 RAM 的 10% 时开始写出脏缓存:0.77G。当脏缓存达到 RAM 的 20%:1.54G 时,缓冲的 write() 调用应该阻塞。
我跑过去dd if=/dev/zero of=~/test bs=1M count=2000看着dirty田野atop。当dd命令运行时,该dirty值稳定在 0.5G 左右。这明显低于脏背景阈值(0.77G)!怎么会这样?我错过了什么?
dirty_expire_centisecs是 3000,所以我认为这不是原因。我什至尝试降低dirty_expire_centisecs到 100 和dirty_writeback_centisecs10,看看这是否是限制dirty。这并没有改变结果。
作为调查的一部分,我最初写下了这些观察结果:为什么在 2013 年报告了“USB 记忆棒停顿”问题?为什么现有的“No-I/O 脏节流”代码没有解决这个问题?
我知道在两个阈值之间的中间 - 15% = 1.155G - write() 调用开始在曲线上受到限制(延迟)。但是在这个天花板之下时不会增加延迟;允许生成脏页的进程“自由运行”。
据我了解,节流旨在将脏缓存保持在 15% 或以上,并防止达到 20% 的硬限制。它并不为每种情况提供保证。但我正在用一个dd命令测试一个简单的案例;我认为它应该简单地限制 write() 调用以匹配设备实现的写出速度。 …
我有一个/dev/mydisk基于一系列功能的设备:LUKS 加密的软件 RAID-1。
有时,我/dev/mydisk会将内容备份到外部 USB 磁盘,该磁盘本身使用 LUKS 加密。需要传输几个 100 GiB。这个操作不是简单的dd而是递归的cp(我还是需要改用rsync)
备份开始一段时间后,整个系统的交互性急剧下降。KDE 接口显然在等待获得批准的内存请求而窒息而死。提示的等待时间为 2 分钟并不罕见。等待网络 I/O 同样需要很大的耐心。这与baloo启动并决定解压缩每个 zip 并为每个文件内容编制索引以用于未知目的时发生的行为类似:系统变成沼泽独木舟。
内核似乎将所有 RAM 提供给复制进程,并且不愿意将其交还给交互式进程一个机会。RAM 并不寒酸:23 GiB。还有 11 GiB 的交换空间,以防万一,但它随时都会被几个 MiB 占用。
是否可以确保交互式进程优先于复制进程获得它们的 RAM?如果是这样,如何?
版本信息:
感谢大家到目前为止的答案!
一旦知道要搜索什么,就会发现一些东西。
我拖进来的东西:
dd,补救方法是使用标志oflag=direct绕过页面缓存。我最近检查了一个几乎完全挂起的 RHEL7.2,因为它写入了 CIFS 文件系统。dirty_ratio = 30和 cifs的默认设置被缓存(用于读取和写入),这些脏页大多是 cifs 的。
在内存压力下,当系统回收大部分读缓存时,系统顽固地尝试刷新和回收脏(写)缓存。所以情况是一个巨大的 CPU iowait 伴随着极好的本地磁盘 I/O 完成时间,D 中的许多进程不间断等待和一个完全无响应的系统。OOM杀手从来没有从事过,因为是免费的内存系统没有给出来。(我认为 CIFS 也有一个错误,它使刷新速度慢得令人难以置信。但别介意这里。)
我惊讶地发现内核处理刷新页面到一些慢速远程 CIFS 盒的方式与处理超快速本地 SSD 驱动器完全相同。拥有一个dirty_ratio包是不明智的,它很快就会导致 30% 的 RAM 包含来自最慢设备的脏数据的情况。真是浪费钱。
这种情况是可重现的;设置dirty_ratio = 1彻底解决问题。但是为什么我需要因为使用cifs挂载而牺牲本地磁盘的缓存?
除了完全禁用某些设备的缓存或设置vm.dirty_ratio为非常低的值之外,还有什么方法可以将快速设备“列入白名单”以获得更多写入缓存?或者让慢速设备(或像 //cifs/paths 这样的远程“设备”)使用更少的写缓存?
RHEL 7.2 的内核版本称为 3.10.0-327。(它基于 3.10.0,但包括数年的向后移植)。