LINUX.ORG.RU

C++: атомарно добавить в файл 128MB данных.

 ,


0

2

Предложите алгоритм.

Хочется добавить в файл 128MB данных, чтобы это переживало отрубание питалова в любой момент с такими последствиями: либо я вижу консистентные 128MB добавленных данных, либо я вижу некий кусок мусора с консистентным заголовком, из которого ясно какого точно размера мусор.

«добавить в файл» не означает строго то, что файл надо открыть в режиме O_APPEND и буквально добавить. Файл на пару гигов можно выделить заранее и манипулировать какими-то страницами в нём.

Т.е. хочется чего-то типа double-buffer, когда сначала куча страниц пишется в специальную временную область файла, потом вызывается fsync(), а потом они пишутся в нормальное место. Если в процессе записи в нормальное место рубанут питалово, то процесс находит во временном буфере то, что недописалось в «нормальное место» и пишет это туда. Ну в общем, интересуют всякие такие истории, не буквально этот подход.

Вся эта тема предполагает некоторые атомарные операции с файлом (сектор HDD, меньше которого нельзя записать; или даже несколько дорог в черепичной записи, меньше которых черепичный HDD не умеет записывать). Скажем, если размер атомарной записи = 512 байт, то нужно ещё и выравнивать - нельзя с позиции 12 записать 512 байт, ведь такая запист будет физически из 2 кусков - 512 + 512 — первый для 500, второй для 12.

Короче, куда копать?

А заказчику не проще будет поставить бесперебойник?

Norgat ★★★★★
()

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

unt1tled ★★★★
()
Ответ на: комментарий от gag

Теоретически можно, например, поставить 128 МБ очень качественной флеш-памяти, ибо на такой объём она копеечная. И по-быстрому перенести кеш туда.

KivApple ★★★★★
()
Ответ на: комментарий от hlamotron

Отрезать весь конец с непонятным содержимым, не?

KivApple ★★★★★
()
Ответ на: комментарий от unt1tled

Самое разумное предложение. В итоге вся ответственность перекладывается на ОС. Ещё можно писать сначала в /tmp/myfile.tmp, а после полной записи делать mv на /var/myapp/data/data%i.dat. В результате, возможно, даже без контрольных сумм всё будет неплохо. А с ними вообще замечательно.

KivApple ★★★★★
()
Последнее исправление: KivApple (всего исправлений: 1)
Ответ на: комментарий от hlamotron

fsync

по моему скромному опыту с линуксами, обойти кэш и заставить это ядро напрямую записать данные на диск реально только с fadvise (с POSIX_FADV_DONTNEED)

demidrol ★★★★★
()
Ответ на: комментарий от pon4ik

Просто сброс страницы вроде как атомарный в mmap, но я могу путать с виндой.

mmap от write в этом плане особо ничем не отличается.

mv ★★★★★
()
Ответ на: комментарий от demidrol

по моему скромному опыту с линуксами, обойти кэш и заставить это ядро напрямую записать данные на диск реально только с fadvise (с POSIX_FADV_DONTNEED)

O_DIRECT, вообще-то.

mv ★★★★★
()

128MB? А не проще писать каждый такой блок в отдельный файл по имени «block0000010.uncommitted» и потом закрывать и переименовывать в «block0000010»

vertexua ★★★★★
()

Пиши в первый блок файла его размер. Тогда весь алгоритм сводится к:

открыть файл
обрезать длину файла по размеру в заголовке
дописать 128Мб
fsync
перейти в начало файла
записать новую длину
monk ★★★★★
()
Ответ на: комментарий от demidrol

ну и вот lkml

Да-да, от создателя page cache, и «делайте huge pages через файловую систему».

mv ★★★★★
()
Ответ на: комментарий от monk

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

Deleted
()
Ответ на: комментарий от arkhnchul

Запасает немного электричества. Плюс, энергию вращения немного юзает как источник энергии. Это круче швейцарских часов, за разглашение инженерной реализации расстреливают в лесу.

hlamotron
() автор топика
Ответ на: комментарий от hlamotron

это сейчас серьезно было, «у нас есть таааакие технологии, но никому не покажем», еще и рекуперация до кучи? На железных RAID контроллерах «с батарейками» или ионисторами еще хоть как-то возможно, но сам по себе диск емнип тупо механически паркует головки при обломе питания.

arkhnchul ★★★
()
Вы не можете добавлять комментарии в эту тему. Тема перемещена в архив.