Какова философия задерживания записи данных на диск?

В Linux завершенное выполнение команды, такой как cp или dd , не означает, что данные были записаны на устройство. Нужно, например, вызвать sync или вызвать функцию «Безопасное удаление» или «Извлечь» на диске.

Какова философия такого подхода? Почему данные не записываются сразу? Существует ли опасность того, что запись не завершится из-за ошибки ввода-вывода?

    11 Solutions collect form web for “Какова философия задерживания записи данных на диск?”

    Какова философия такого подхода?

    Эффективность (лучшее использование характеристик диска) и производительность (позволяет приложению продолжить работу сразу после записи).

    Почему данные не записываются сразу?

    Основным преимуществом является то, что ОС может свободно изменять порядок и объединять непрерывные операции записи, чтобы улучшить использование полосы пропускания (меньше операций и меньше запросов). Жесткие диски работают лучше, когда запрашивается небольшое количество больших операций, в то время как приложения, как правило, нуждаются в большом количестве небольших операций. Еще одна явная оптимизация – OS также может удалить все, кроме последней записи, когда один и тот же блок записывается несколько раз за короткий промежуток времени или даже удаляет некоторые записи вместе, если затронутый файл был удален в то же время.

    Эти асинхронные записи выполняются после возврата системного вызова write . Это второе и наиболее очевидное преимущество пользователя. Асинхронная запись ускоряет работу приложений, так как они могут продолжать свою работу, не дожидаясь, пока данные действительно будут на диске. Такой же тип буферизации / кэширования также реализуется для операций чтения, когда недавно или часто считываемые блоки сохраняются в памяти вместо того, чтобы читать их снова с диска.

    Существует ли опасность того, что запись не завершится из-за ошибки ввода-вывода?

    Не обязательно. Это зависит от используемой файловой системы и избыточности. Ошибка ввода-вывода может быть безобидной, если данные можно сохранить в другом месте. Современные файловые системы, такие как ZFS, сами восстанавливают блоки блокировки. Также обратите внимание, что ошибки ввода-вывода не приводят к сбою современных ОС. Если они происходят во время доступа к данным, они просто сообщаются затрагиваемому приложению. Если они происходят во время структурного доступа к метаданным и подвергли файловую систему риску, она может быть переделана только для чтения или сделана недоступной.

    Также существует небольшой риск потери данных в случае сбоя ОС, сбоя питания или сбоя оборудования. Именно поэтому приложения, которые должны быть на 100% уверены, что данные находятся на диске (например, базы данных / финансовые приложения), делают менее эффективную, но более безопасную синхронную запись. Чтобы уменьшить влияние производительности, многие приложения по-прежнему используют асинхронную запись, но в конечном итоге синхронизируют их, когда пользователь сохраняет явно файл (например, vim, текстовые процессоры).

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

    Наконец, синхронной записи недостаточно для защиты записанных данных. Если ваше приложение действительно должно быть уверенным, что их данные не могут быть потеряны, что бы ни случилось, необходимо реплицировать данные на нескольких дисках и в нескольких географических точках, чтобы противостоять катастрофам, таким как пожар, наводнение и т. Д.

    Это просто дает иллюзию скорости программам, которые на самом деле не должны ждать завершения записи. Установите свои файловые системы в режиме синхронизации (что дает вам мгновенные записи) и посмотрите, насколько медленным все.

    Иногда файлы существуют только временно … программа выполняет некоторую работу и удаляет файл сразу после завершения работы. Если вы задерживаете эти записи, вы можете уйти, не написав их в первую очередь.

    Существует ли опасность того, что запись не завершится из-за ошибки ввода-вывода?

    О, абсолютно. В таком случае обычно вся файловая система переходит в режим только для чтения, и все ужасно. Но это редко случается, нет смысла проигрывать преимущества производительности в целом.

    Асинхронный буферизованный ввод-вывод использовался до Linux и даже до Unix. У Unix это было, и у всех есть свои ответвления.

    Вот что написал Ричи и Томпсон в своей статье CACM. Система распределения времени UNIX :

    Для пользователя как чтение, так и запись файлов выглядят синхронными и небуферизованными. Это сразу же после возврата из прочитанного вызова доступны данные, и, наоборот, после записи рабочее пространство пользователя может быть повторно использовано. Фактически система поддерживает довольно сложный механизм буферизации, который значительно сокращает количество операций ввода-вывода, необходимых для доступа к файлу.


    В вашем вопросе вы также писали:

    Существует ли опасность того, что запись не завершится из-за ошибки ввода-вывода?

    Да, запись может завершиться неудачно, и программа, возможно, никогда не узнает об этом. Хотя это и не очень хорошо, последствия этого могут быть сведены к минимуму в тех случаях, когда ошибка ввода-вывода создает системную панику (на некоторых ОС это настраивается – вместо того, чтобы паниковать, система может продолжать работать, но затронутая файловая система размонтирован или смонтирован только для чтения). Затем пользователи могут получать уведомления о том, что данные в этой файловой системе являются подозрительными. И на жестком диске можно проконтролировать, будет ли его растущий список дефектов быстро увеличиваться, что свидетельствует о сбое диска.

    BSD добавила системный вызов fsync чтобы программа могла убедиться, что данные файла были полностью записаны на диск перед продолжением, а последующие Unix-системы предоставили опции для синхронной записи. GNU dd имеет параметр conv=fsync чтобы убедиться, что все данные были выписаны до выхода команды. Это пригодится при записи на медленные съемные флеш-накопители, где буферизованные данные могут занять несколько минут.

    Другим источником повреждения файлов является внезапное отключение системы, например, от потери мощности. Практически все текущие системы поддерживают чистый / грязный флаг в своих файловых системах. Флаг установлен на очистку, когда нет данных для записи и файловая система должна быть размонтирована, как правило, во время выключения системы или путем ручного вызова umount . Системы, как правило, запускают fsck при перезагрузке, если обнаруживают, что файловые системы не были закрыты чисто.

    Много хороших ответов, но позвольте мне добавить еще одну вещь … Помните, что Unix – это многопроцессорная и многопользовательская система, поэтому потенциально многие пользователи будут пытаться выполнять файловые операции (esp. Write) на (почти) в то же время. Благодаря старым медленным жестким дискам – возможно, установленным по сети – это не только займет время (для которых программы будут в основном заблокированы, и пользователи должны будут ждать), но заставляют много перемещать чтение / запись заголовка диск взад и вперед.

    Поэтому вместо этого файлы, ожидающие записи, некоторое время сохранялись в памяти и сортировались после того, как они должны были закончиться на диске … и когда буфер был заполнен – ​​или демон-дисковая синхронизация ждал требуемое количество секунд (я думаю, что это обычно составляло около 30 секунд) – весь буфер был записан на диск «по порядку», при этом голова записи должна была делать одно непрерывное движение, записывая файлы на диск как он пошел … вместо того, чтобы прыгать повсюду.

    В курсе сегодняшних быстрых дисков – не говоря уже о твердотельных устройствах – выигрыш намного меньше … особенно в домашней Linux-системе, где есть только один пользователь, работающий одновременно, и только с несколькими программами.

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

    Он не специфичен для Linux, и он называется кэшем страницы (что делает Linux довольно хорошо). См. Также http://linuxatemyram.com/ ; поэтому, если файл написан, то через несколько секунд снова прочитайте, очень часто не требуется ввод-вывод с диска.

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

    Код приложения может давать подсказки относительно этого кэширования: см., Например, posix_fadvise (2) & madvise (2)

    Спиннинг пластин медленнее, чем ОЗУ. Мы используем кеширование чтения / записи для «скрытия» этого факта.

    Полезная вещь о записи IO заключается в том, что он не требует немедленного запуска диска IO – в отличие от чтения, где вы не можете вернуть данные пользователю до тех пор, пока чтение не будет завершено на диске.

    Таким образом, записи работают в условиях ограниченного времени – до тех пор, пока наша устойчивая пропускная способность не будет больше, чем у нашего диска, мы можем скрыть много штрафов за производительность в кеше записи.

    И нам нужно писать кеширование – вращающиеся диски очень медленны сравнительно. Но так, чтобы современные типы RAID имели значительный штраф за работу.

    Например, RAID 6, чтобы завершить одно сообщение, должен:

    • Чтение блока обновления
    • читать паритет1
    • читать паритет 2
    • написать новый блок
    • написать паритет 1
    • написать паритет 2

    Таким образом, каждая запись – это фактически 6 операций ввода-вывода – и особенно когда у вас медленные диски, такие как большие диски SATA, это становится чрезвычайно дорогостоящим.

    Но есть приятное легкое решение – написать коалесценцию. Если вы можете создать «полную полосу» записи в буфере, вам не нужно читать четность с вашего диска – вы можете вычислить его на основе того, что у вас есть в памяти.

    Это очень желательно сделать, потому что тогда у вас больше нет усиления записи. В самом деле, вы можете получить более низкое количество штрафов за запись, чем RAID 1 + 0.

    Рассматривать:

    RAID 6, 8 + 2 – 10 шпинделей.

    8 последовательных блоков данных для записи – вычислять четность в кеше и записывать один блок на каждый диск. 10 записей на 8, означает штраф за запись в размере 1,25. 10 дисков RAID 1 + 0 по-прежнему имеют штраф за запись в 2 (потому что вы должны писать в каждое подчинение). Таким образом, в этом случае вы можете сделать RAID 6 лучше, чем RAID1 + 0. В реальном мире вы получаете немного больше смешанного профиля IO.

    Таким образом, кэширование записи имеет огромное значение для восприятия производительности RAID-массивов – вы можете писать на скорости RAM и иметь низкую штрафную запись – улучшая свою устойчивую пропускную способность, если вы это сделаете.

    И если вы этого не сделаете, вы понесете медленную производительность SATA, но умножьте ее на 6 и добавьте в нее некоторые разногласия. Ваш 10-портовый SATA RAID-6 без кэширования записей будет немного быстрее, чем один диск без RAID … но не очень.

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

    Ни один из других ответов не упоминал о задержке распределения . XFS, ext4, BTRFS и ZFS все это используют. XFS использует его с тех пор, пока не существовал ext4, поэтому я буду использовать его в качестве примера:

    XFS даже не решает, куда помещать данные до выписки. Отсроченное распределение дает распределителю гораздо больше информации для принятия своих решений. Когда файл сначала записывается, нет никакого способа узнать, будет ли он файлом 4k или файлом 1G и все еще растущим. Если есть 10G смежного свободного места где-то, поместив файл 4k в начале, это не принесет пользы. Помещение большого файла в начале большого свободного места уменьшает фрагментацию.

    Все остальные ответы здесь, как минимум, в основном правильны для нормального случая, и я бы рекомендовал прочитать любой из них до моего, но вы упомянули, что dd и dd имеют типичный прецедент, который может не включать кэширование записи. Кэширование записи в основном реализовано на уровне файловой системы. Необработанные устройства обычно не кэшируют запись (многие драйверы устройств, такие как raid или lvm, являются еще одним шариком воска). Поскольку dd часто используется с необработанными блочными устройствами, он предоставляет параметры bs и связанные с ними параметры, позволяющие делать большие записи для повышения производительности на необработанных устройствах. Это не так полезно, когда обе конечные точки являются обычными файлами (хотя в этом случае большие записи используют меньше системных вызовов). Другим распространенным местом, где это особенно заметно, является пакет mtools, который является реализацией файловой системы живого пространства пользователей. использование mtools с гибким диском всегда кажется невероятно вялым, поскольку инструменты полностью синхронны, а флоппи-дисководы невероятно медленны. Установка флоппи-диска и использование файловой системы с жирным массивом гораздо более отзывчивы, за исключением umount, который является синхронным (и очень важным для этого является предотвращение потери данных, особенно для съемных устройств, таких как дискеты). Есть только несколько других программ, которые, как мне известно, регулярно используются с необработанными устройствами, такими как специально сконфигурированные базы данных (которые реализуют собственное кэширование записи), tar и специальные устройства и инструменты для файловой системы, такие как chdsk, mkfs и mt.

    Философия небезопасна по умолчанию.

    Возможны две разумные и очевидные стратегии: сброс записи на диск немедленно или задержка записи. UNIX исторически выбрала последнее. Так что получите безопасность, вам нужно позвонить fsync впоследствии.

    Однако вы можете указать безопасность заранее, установив устройство с опцией sync или per-file, открыв их с помощью O_SYNC .

    Помните, что UNIX был разработан для компьютерных экспертов. «Безопасный по умолчанию» не был рассмотрен. Безопасность означает более медленный ввод-вывод, и эти ранние системы действительно имели медленный ввод-вывод, повышающий цену. К сожалению, ни UNIX, ни Linux не переключились на безопасное дефолт, хотя это непереломное изменение.

    Он торгует небольшим количеством надежности для значительного увеличения пропускной способности.

    Предположим, например, программу сжатия видео. С задержкой записи («write back»):

    1. потратьте сжатие 10 мс
    2. создать кадр записи на диск
    3. подождите 10 мс, чтобы диск подтвердил, что запись завершена
    4. GOTO 1

    Против

    1. потратьте сжатие 10 мс
    2. создать кадр записи на диск (завершается в фоновом режиме)
    3. GOTO 1

    Вторая версия появляется в два раза быстрее, поскольку она может одновременно использовать процессор и диск, в то время как первая версия всегда ждет того или другого.

    Как правило, вы хотите выполнить обратную запись для потоковых операций и операций с массовыми файлами, а также для записи данных для баз данных и приложений, подобных базам данных.

    Во многих приложениях запоминающие устройства будут периодически заняты чтением данных. Если система всегда может откладывать записи до тех пор, пока запоминающее устройство не будет занято чтением данных, то с точки зрения приложения запись займет нулевое время. Единственные ситуации, когда записи не были мгновенными, будут:

    1. Буферы записи заполняются до такой степени, что больше запросов на отложенную запись не могут быть приняты до тех пор, пока записи не будут полностью завершены.

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

    3. Приложение специально запрашивает подтверждение того, что запись действительно завершена.

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

    Interesting Posts

    как перенаправить все электронные письма на один внешний адрес?

    Сценарий установки должен выполняться как определенный (обычный) пользователь, но ему необходимо создать системный каталог

    Виртуальная коробка для centos PAE

    Почему обязательные утилиты POSIX не встроены в оболочку?

    Не удается подключиться к ethernet на кабельном модемом

    Предел памяти JVM для Linux (Debian)

    Блокировать все IP-адреса от доступа к чему-либо на сервере

    Как просыпаться монитор от bash?

    Необходимо распечатать соответствующие строки в другом файле

    Подпроцессы nodejs в скрипте nohup bash заблокированы

    javac показывает другую версию на Fedora 23

    Подстановочные знаки: как я могу перечислить файлы, заканчивающиеся на `.txt`, только без использования символа точки?

    Как приостановить MySQL, прежде чем делать снимок LVM / ZFS?

    загрузочный live usb не загружается, KNOPPIX

    неправильный тип fs, неправильная опция, плохой суперблок при попытке монтировать восстановленный том

    Linux и Unix - лучшая ОС в мире.