У меня есть сжатие Debian (2.6.32-5-amd64), которое одновременно является сервером и клиентом NFS4 (монтируется через NFS4). Локальный каталог, который ведет прямо на диск, /nfs4exports/mydir
, в то время как /nfs4mounts/mydir
то же самое, монтируется через NFS, используя внешний IP-адрес машины. Вот строка из fstab
:
192.168.1.75:/mydir /nfs4mounts/mydir nfs4 soft 0 0
У меня есть приложение, которое записывает много маленьких файлов. Если я напишу прямо на /nfs4exports/mydir
, он записывает тысячи файлов в секунду; но если я напишу /nfs4mounts/mydir
, он записывает 4 файла в секунду или около того. Я могу значительно увеличить скорость, если добавлю async
к /etc/exports
. (Запись одного большого файла в каталог, смонтированный по NFS, идет со скоростью более 100 МБ / с.)
Я просматриваю статистику сервера и вижу, что всякий раз, когда файл записывается, он «фиксируется» (это также происходит с NFSv3):
root@debianvboxtest:~# mount -t nfs4 192.168.1.75:/mydir /mnt
root@debianvboxtest:~# nfsstat|grep -A 2 'nfs v4 operations'
Server nfs v4 operations:
op0-unused op1-unused op2-future access close commit
0 0% 0 0% 0 0% 10 4% 1 0% 1 0%
root@debianvboxtest:~# echo 'hello' >/mnt/test1056
root@debianvboxtest:~# nfsstat|grep -A 2 'nfs v4 operations'
Server nfs v4 operations:
op0-unused op1-unused op2-future access close commit
0 0% 0 0% 0 0% 11 4% 2 0% 2 0%
Сейчас в RFC, Я прочитал это:
Операция COMMIT аналогична по работе и семантике системному вызову POSIX fsync (2), который синхронизирует состояние файла с диском (данные файла и метаданные сбрасываются на диск или в стабильное хранилище). COMMIT выполняет ту же операцию для клиента, сбрасывая все несинхронизированные данные и метаданные на сервере на диск сервера или в стабильное хранилище для указанного файла.
Я не понимаю, почему клиент соглашается. Я не думаю, что встроенная команда оболочки "echo" запускается fsync
; если echo
записал в локальный файл, а затем машина вышла из строя, файл мог быть потерян. Напротив, клиент NFS, похоже, отправляет COMMIT после завершения echo
. Зачем?
Я не хочу использовать async
Вариант сервера NFS, потому что он явно проигнорирует COMMIT. Мне кажется, что у меня была локальная файловая система, и мне приходилось выбирать между синхронизацией каждого файла при закрытии и игнорированием fsync
все вместе. Что я неправильно понял?
потому что именно так работает NFS, и именно так она должна работать, поскольку это синхронный протокол. Что вам нужно убедиться, так это то, что экспортируемая файловая система поддерживается LUN, которые имеют защиту NVRAM / BBWC и правильно обрабатывают fsync () - т.е. игнорируют это и маскируют флаги SCSI FUA и команды SCSI_CACHE_SYNCHRONIZE. Также убедитесь, что в файловой системе не включены барьеры, если она поддерживается BBWC / NVRAM.
Таким образом, NFS сохраняет свою синхронную семантику и эквивалентна запуску fsync () после каждой записи, но вы получаете производительность асинхронной работы.