В любой файловой системе реализован механизм копирования при записи для CP

16

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

То же самое происходит и при выполнении CP на linux с файловыми системами ext4 или xfs (ведение журнала). Если это не происходит, то почему бы и нет?

Мридуль Верма
источник
Надеюсь, кто-нибудь ответит на этот интересный вопрос
Карим Манауй
Однако я так не думаю, потому что, например, копирование большого файла займет значительно больше времени (копирование данных в новые блоки). Если бы в таких файловых системах был COW (по крайней мере, ext3 / ext4), вы бы не заметили задержку по времени (может быть, в таком случае только репликация индекса без указателей на блоки данных и пометка некоторого флага COW).
Карим Манауй
Копирование при записи реализовано в ZFS, и у него действительно очень дешевые клоны файловой системы / тома. У ext4 / xfs есть слишком примитивный формат на диске, я думаю, чтобы поддержать это
myaut

Ответы:

7

Ключевое слово для поиска является reflink. Это было недавно реализовано в XFS.

РЕДАКТИРОВАТЬ: реализация XFS была первоначально помечена как ЭКСПЕРИМЕНТАЛЬНАЯ. Это предупреждение было удалено в версии ядра 4.16, через несколько месяцев после того, как я написал выше :-).

sourcejedi
источник
11

С cp man-страницы :

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

Это работает на файловых системах, которые поддерживают Copy-on-Write ( reflink ), в основном BTRFS на данный момент. Реализация ссылки XFS находится в разработке [1] [2] .

sebasth
источник
1
Некоторые сетевые файловые системы, такие как NFS, CIFS, OCFS2, также могут передавать их на сервер.
Стефан
2

В Linux есть системный вызов, который позволяет процессам в пользовательском пространстве сообщать ядру о копировании при записи копий файлов. FICLONERANGE и FICLONE, используемые в качестве опций для ioctl, позволяют копировать при записи копии файлов и диапазонов внутри файлов.

Это используется cp --reflink, чтобы сделать копии, где файловая система поддерживает это.

Q утконос
источник
1

Если вы не введете системный вызов для cp(или, по крайней мере, для копирования блока), ОС будет трудно понять, что данные, которые cpпрограмма собирается записать, совпадают с данными, которые она только что прочитала из другого блока. Кроме того, у вас будут дополнительные издержки для управления сценарием «несколько файлов совместно используют одни и те же блоки». Большие похожие файлы, которые отличаются только несколькими блоками, встречаются редко. Таким образом, в целом дешевле просто скопировать эти блоки, а затем добавить административные издержки ко всем файлам.

Теперь, если вы «копируете» файлы (их много), добавляя еще один клон / снимок файловой системы, скажем, в BTRFS, ситуация другая: теперь вы «скопировали» все файлы в файловой системе, и любые изменения в они будут копировать при записи. Это существует, но не в ext4.

«Журналирование» является полностью независимым понятием от того, что учитываются административные структуры для файлов.

dirkt
источник
Большие файлы, один из которых является двоичной копией другого, очень редкие времена отличаются одним битом, и это происходит из-за ошибки.
битифет
Был введен системный вызов для копирования (см. Мой ответ).
Q Утконос