Почему чтение / dev / zero не считается как IO_RBYTES?

25

Я освобождаю жесткий диск на некоторых ОС Linux 4.x с помощью этой команды:

sudo sh -c 'pv -pterb /dev/zero > /dev/sda'

И я открыл другой tty и начал sudo htopи заметил это:

  PID USER      PRI  NI CPU%   RES   SHR   IO_RBYTES   IO_WBYTES S   TIME+  Command
 4598 root       20   0 15.5  1820  1596        4096    17223823 D  1:14.11 pv -pterb /dev/zero

Значение для IO_WBYTESкажется вполне нормальным, но IO_RBYTESостается на уровне 4 КиБ и никогда не меняется.

Я запустил несколько других программ, например

dd if=/dev/zero of=/dev/zero
cat /dev/zero > /dev/zero

и был удивлен, увидев, что ни один из них не генерирует много IO_RBYTESили IO_WBYTES.

Я думаю, что это не относится к какой-либо программе, но почему бы не считывать /dev/zeroи записывать, чтобы /dev/{zero,null}считаться байтами ввода / вывода?

iBug
источник
5
Мне любопытно, почему вы думаете, что они должны считаться I / O?
marcelm
1
@marcelm Я думаю, что любой ввод / вывод должен учитываться как ввод / вывод, включая файловый R / W, сетевой ввод / вывод и многое другое.
iBug
но эти операции выполняют ввод / вывод на аппаратном обеспечении (диск и сетевая карта, соответственно) и должны проходить через некоторую шину ввода / вывода (например, PCI-express), что может быть существенным узким местом. Пишет, скажем, /dev/nullне в конечном итоге интерфейс с таким оборудованием и не забивает шины ввода-вывода. Взятый до крайности; чтение / запись в / из памяти также ввод / вывод? Конечно, нет четкого разграничения для этих вещей, и все зависит от того, какую перспективу вы принимаете в этих вещах, и насколько полезной эта перспектива оказывается для вас.
Марсель
1
Обратите внимание, что мой первый комментарий был направлен на то, чтобы спровоцировать вас (и других) подумать об этих перспективах и выяснить, почему вы придерживаетесь своей точки зрения. Я не имею в виду, что вы не правы; Я даже не думаю, что ситуация такая черная и белая. Но лично я был бы гораздо больше заинтересован в статистике ввода-вывода для реального оборудования (которое может быть очень узким местом), чем для /dev/{null,zero}(которое обычно не является узким местом). Это только моя точка зрения, хотя :)
Marcelm
1
@marcelm Но я изначально думал, что any read(2)и write(2)считается I / O, что очень разумно в своем собственном смысле.
iBug

Ответы:

54

Они считаются вводом / выводом, но не того типа, который измеряется полями, на которые вы смотрите.

В htop, IO_RBYTESи IO_WBYTESпоказать read_bytesи write_bytesполя из /proc/<pid>/io, и эти поля измерения байтов , которые проходят через блок слоя. /dev/zeroне включает в себя блочный слой, поэтому чтение из него там не отображается.

Чтобы увидеть ввод / вывод из /dev/zero, вам нужно взглянуть на поля rcharи , которые отображаются в виде и :wchar/proc/<pid>/iohtopRCHARWCHAR

rchar : прочитанные символы

Число байтов, которые эта задача вызвала для чтения из хранилища. Это просто сумма байтов, которые этот процесс передал read(2)и подобные системные вызовы. Он включает в себя такие вещи, как терминальный ввод-вывод и не зависит от того, требовался ли фактический физический дисковый ввод-вывод (чтение могло быть выполнено из pagecache).

wchar : написанные символы

Количество байтов, которое эта задача вызвала или должна записать на диск. Подобные предостережения применимы здесь как с rchar.

Смотрите man 5 procи man 1 htopдля деталей.

Стивен Китт
источник
Так что это rcharи wcharчто подсчет байтов от звонков read(2)и write(2), не так ли?
iBug
Да все верно.
Стивен Китт
9
Поговорим о вводящей в заблуждение фразировке в описании rchar . Все, что прошло, read()определенно не «прочитано из хранилища »!
ilkkachu
2
@ilkkachu storageони означают «любая мыслимая линия шины», независимо от того, является ли рассматриваемое хранилище физическим или виртуальным, или mmap'd, или виртуальным сокетом, или в кеше L1 - это просто что-то вне отображаемой памяти этой программы, включая shared
cat