Создание незагруженных файловых буферов вывода - PullRequest
3 голосов
/ 22 августа 2011

Я пытаюсь разрешить проблему, которая возникает с буферами ввода-вывода в нечетких файлах в нескольких программах на разных языках, работающих в Linux.Решение по очистке буферов достаточно простое, но эта проблема незаполненных буферов происходит совершенно случайно.Вместо того, чтобы обращаться за помощью к тому, что может вызвать это, меня интересует, как создать (воспроизвести) и диагностировать ситуацию такого рода.

Это приводит к вопросу из двух частей:

  1. Возможно ли искусственно и легко построить экземпляры, в которых в течение заданного периода времени можно иметь выходные буферы, для которых известно, что не обнулено?Мои поиски оказываются пустыми.Тривиальная базовая линия - забить жесткий диск (например, подкачку) в одном процессе, пытаясь записать большое количество данных из другого процесса.Хотя это «работает», это делает систему практически непригодной для использования: я не могу осмотреться и посмотреть, что происходит.

  2. Существуют ли в Linux команды, которые могут идентифицировать данный процессесть незаполненные буферы вывода файла?Это что-то, что может быть запущено из командной строки, или это необходимо для непосредственного запроса к ядру?Я смотрел на fsync, sync, ioctl, flush, bdflush и других.Однако, не имея метода для создания незаполненных буферов, неясно, что они могут показать.

Чтобы воспроизвести для других, пример для # 1 в C был бы превосходным, новопрос действительно не зависит от языка - просто знание подхода к созданию такой ситуации помогло бы на других языках, на которых я работаю.


Обновление 1. Мои извинения за любую путаницу.Как отметили несколько человек, буферы могут находиться в пространстве ядра или в пространстве пользователя.Это помогло точно определить проблемы: мы создаем большие грязные буферы ядра.Это различие и ответы полностью решают вопрос № 1: теперь кажется ясным, как воссоздать незаполненные буферы либо в пространстве пользователя, либо в пространстве ядра.Однако определить, какой идентификатор процесса имеет грязные буферы ядра, пока не ясно.

Ответы [ 3 ]

1 голос
/ 22 августа 2011

Очень легко создавать незаполненные буферы, управляя принимающей стороной.Прелесть систем * nix в том, что все выглядит как файл, поэтому вы можете использовать специальные файлы, чтобы делать то, что вы хотите.Самый простой вариант - это труба.Если вы просто хотите управлять стандартным выводом, это простой вариант: unflushed_program | slow_consumer.В противном случае вы можете использовать именованные каналы:

mkfifo pipe_file
unflushed_program --output pipe_file
slow_consumer --input pipe_file

slow_consumer, скорее всего, это программа, которую вы разрабатываете для медленного чтения данных или просто для чтения X байтов и остановки.

1 голос
/ 22 августа 2011

Если вас интересуют данные, буферизованные ядром, вы можете настроить обратную запись виртуальной машины через sysctls в /proc/sys/vm/dirty_*. В частности, dirty_expire_centisecs - это возраст в сотых долях секунды, при котором грязные данные становятся пригодными для обратной записи. Увеличение этого значения даст вам больше времени для расследования. Вы также можете увеличить dirty_ratio и dirty_background_ratio (которые являются процентами системной памяти, определяя точку, в которой синхронная и асинхронная обратная запись начинается соответственно).

На самом деле создать грязные страницы очень просто - просто write(2) в файл и выйти без синхронизации, или испачкать некоторые страницы в MAP_SHARED отображении файла.

1 голос
/ 22 августа 2011

Простая программа, которая будет иметь незаполненный буфер, будет выглядеть так:

main()
{
      printf("moo");
      pause();
}

Stdio, по умолчанию только сбрасывает стандартный вывод на новых строках при подключении к терминалу.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...