Дзвінок завжди починається однаково: «Ми додали дисків, сховище тепер велике, а продуктивність погіршилася. Чи потрібен нам 1 ГБ ОЗП на ТБ?»
Потім хтось пересилає скріншот з форуму, ніби це нотаріально завірений план ємності.
Розмір ARC — це не астрологія. Це економіка кешу, фізика навантаження і трохи смиренності щодо того, що насправді робить ZFS.
Якщо ви підбиратимете ОЗП, рахуючи просто терабайти, то в деяких середовищах переплатите, а в інших все одно будете повільними.
Давайте замінимо фольклор на рішення, які ви зможете захистити у рев’ю змін.
Припиніть використовувати «ОЗП на ТБ» як правило підбору
«1 ГБ ОЗП на ТБ зберігання» — це еквівалент фрази «перезавантажте і подивіться, чи допоможе». Інколи це випадково спрацьовує, тому й живе.
Але це не метод підбору. Це забобон з одиницею.
ARC — це кеш. Кеші не підбираються за ємністю; вони підбираються під робочий набір і цілі за затримкою.
Ваш пул може бути 20 ТБ холодних архівів, які записуються раз і ніколи не читаються. Або це може бути 20 ТБ віртуальних машин з 4K випадковими читаннями і невеликим гарячим набором, що поміщається в пам’ять.
Ці два світи мають ті самі «ТБ» і зовсім різну «важливу ОЗП».
Ось що пропускає правило по терабайтах:
- Шаблон доступу важливіший за ємність. Послідовні скани можуть перелаштувати будь-який розмір ARC; випадкові читання можуть кардинально покращитися завдяки ARC.
- Метадані мають іншу цінність, ніж дані. Кешування метаданих може зробити «повільний диск» відчутно швидким без великого кешування користувацьких даних.
- У ZFS є регульовані параметри, що змінюють поведінку пам’яті. recordsize, compression, special vdevs, dnodesize та primarycache мають значення.
- ARC конкурує з вашими застосунками. Найкращий розмір ARC — це той, що не голодує реальне робоче навантаження.
Що варто робити натомість — це нудно: визначити ціль продуктивності, спостерігати за поведінкою кешу, підтвердити робочий набір і підібрати ОЗП, щоб досягти цілі.
Якщо ви купуєте обладнання, робіть це з планом і з відкатним сценарієм.
Жарт №1: Якщо ви підбиратимете ARC за терабайтами, зрештою купите сервер, що по суті є обігрівачем з SATA-портами.
ARC: що це таке і чого це не є
ARC — кеш в оперативній пам’яті з урахуванням тиску пам’яті
ARC (Adaptive Replacement Cache) живе в ОЗП. Він кешує як дані, так і метадані, і призначений підлаштовуватися між патернами «недавно використані» і «часто використані».
Та частина «адаптивності» реальна: ARC відстежує кілька списків і використовує ghost-записи, щоб навчитися тому, що він хотів би мати в кеші.
ARC також має співпрацювати з ОС при зростанні тиску пам’яті. На Linux ARC зменшується на основі zfs_arc_max та сигналів про тиск; на FreeBSD інтеграція інша, але теж має уникати повного виснаження.
Тут важливо «має»: вам все одно потрібно перевірити, чи ваша ОС і версія ZFS поводяться коректно в вашому середовищі.
ARC — це не «як ZFS зберігає цілісність пулу»
Цілісність ZFS забезпечується copy-on-write, transaction groups і intent logging (ZIL/SLOG для синхронних операцій). Жодне з цього не вимагає величезного ARC.
Так, ZFS використовує пам’ять для метаданих і ведення обліку, але міф «ZFS потребує тонни ОЗП, щоб не пошкодити дані» — це нісенітниця для сучасних релізів.
Ви можете запускати ZFS з помірною кількістю ОЗП, і він залишиться коректним. Просто може бути повільнішим.
ARC не замінює поганий дизайн I/O
Якщо ваше навантаження на 90% — синхронні записи на повільні диски і у вас немає відповідного SLOG, подвійний ARC цього не врятує.
Якщо вузьке місце — CPU (сжаття, контрольні суми, шифрування) або однопоточний застосунок, ARC не допоможе.
Якщо пул заповнений на 90% і фрагментований, ARC не врятує. ARC — кеш, а не терапевт.
Зміст ARC формується властивостями датасетів
Кешування ZFS не є монолітним. Властивості датасету впливають на те, що кешується і наскільки болючими є промахи:
recordsizeзмінює I/O-ампліфікацію і гранулярність кешованих блоків.primarycacheможна встановити вall,metadataабоnone.compressionзмінює, скільки «логічних» даних поміщається на байт ARC і впливає на CPU.atimeі часті зміни метаданих можуть перетворити читання на додаткові записи.
Один вислів, бо він досі найчіткіше формулює думку:
Надія — не стратегія.
— James Cameron
Підбір за навантаженням: єдина модель, що переживає продакшн
Крок 1: класифікуйте реальне навантаження
«Файловий сервер» — це не опис навантаження. Вам потрібен щонайменше такий рівень деталізації:
- Тип I/O: переважно читання, переважно записи, змішане.
- Семантика записів: sync-важкі (бази даних, NFS з sync), async-важкі (масовий інжест).
- Патерн доступу: випадкові 4K/8K, послідовні, багато маленьких файлів, великі стрімінгові файли.
- Гарячий набір: приблизно скільки даних читається повторно за годину/день.
- Ціль по затримці: «віртуальні машини відчуваються швидко» — не ціль; «p95 латентність читання < 5 ms» — так.
Крок 2: вирішіть, що ви хочете від ARC
ARC може приносити цінність трьома поширеними способами:
- Прискорювати випадкові читання, роздаючи гарячі блоки з ОЗП.
- Прискорювати метадані (перебір директорій, відкриття файлів, операції з малими файлами, перегляд снапшотів).
- Зменшувати кількість seek’ів дисків, перетворюючи повторні читання на попадання в пам’ять і звільняючи диски для записів.
Третій пункт недооцінений: іноді ви «повільні при записах», бо диски зайняті уникальними читаннями.
ARC може опосередковано прискорити записи, знімаючи тиск читань.
Крок 3: оберіть початкову точку, що навмисно консервативна
Практичний базовий рівень (не за ТБ і не як закон):
- Невеликий хост віртуалізації / малий NAS: 16–32 GB ОЗП, потім валідація.
- Загальний вузол віртуалізації з SSD пулом: 64–128 GB ОЗП, якщо очікується локальність читань.
- Великі HDD пули, що обслуговують активні навантаження: пріоритет метаданого кешування і розгляд special vdevs; лише ОЗП може не масштабуватись.
- Бази даних зі sync-записами: ARC допомагає читанням; для записів спочатку фокусуйтеся на SLOG і топології пулу.
Якщо ви не можете пояснити, що саме ARC буде кешувати і чому це важливо, не купуйте ОЗП. Спочатку виміряйте.
Крок 4: зрозумійте, чому «більший ARC» може нашкодити
Великий ARC — це не безкоштовно:
- Тиск пам’яті може штовхнути ОС до свопінгу або реклейм-штормів. Якщо ваш гіпервізор свопиться, ваш «кеш» перетворюється на повільний відмовник.
- Час прогріву збільшується після перезавантажень або фейловерів. Великий ARC означає довше досягнення сталого стану.
- Забруднення кешу від сканів/бекапів може витіснити те, що дійсно важливо, особливо якщо ви дозволяєте кешувати усі дані.
- Обмеження ядра і фрагментація пам’яті можуть стати новою дивною проблемою.
Зручна ментальна модель: «гарячий набір + метадані + запас безпеки»
Розмір ARC, який не принижуватиме вас у постмортемі, зазвичай слідує цій логіці:
- Оцініть гарячий набір: ту частину даних, яка читається повторно в межах вашого вікна затримки.
- Додайте резерв для метаданих: записи директорій, проміжні блоки, dnodes, ZAP-об’єкти. Це сильно залежить від навантаження.
- Залиште пам’ять для ОС і застосунків: page cache (за потреби), накладні гіпервізора, контейнери, бази даних, агенти моніторингу і «те, що ви забули».
- Обмежте ARC: не дозволяйте йому завжди «перемагати». Платить ваша аплікація.
Цікаві факти і історія (бо міфи мають джерела)
- ARC існував задовго до широкого застосування ZFS на Linux. Алгоритм ARC описували в академічному середовищі (IBM) ще до того, як ZFS зробив його відомим у колах зберігання.
- Правило «1 ГБ на ТБ» ймовірно почалося як груба застереження для метаданегенних пулів. Ранні розгортання з великими директоріями на повільних дисках відчували себе жахливо без достатньої ОЗП.
- Ранні версії ZFS були більш пам’яттєво вимогливі й менш налаштовувані. Сучасний OpenZFS покращив облік пам’яті і додав регульовані параметри, як persistent L2ARC і special vdevs.
- L2ARC спочатку не був персистентним через перезавантаження. Це робило його менш цінним для систем, що часто перезавантажувалися; персистентний L2ARC змінив економіку для деяких команд.
- ZIL і SLOG часто неправильно розуміють як «кеш записів». Вони стосуються синхронної семантики, а не прискорення всіх записів. Ця плутанина підживлює погані рішення щодо ОЗП.
- За замовчуванням recordsize вибирали для загальних файлів, а не для VM. Стандартний recordsize, наприклад 128K, історично мав сенс, але випадкові I/O навантаження часто потребують іншого налаштування.
- Special vdevs були введені, щоб вирішити конкретний біль. Поміщення метаданих (і за бажанням малих блоків) на SSD може перевершувати «просто додати ОЗП» у HDD пулах.
- Компресія стала типовою рекомендацією, бо CPU став дешевим. На сучасних процесорах компресія може збільшити ефективну ємність ARC і зменшити I/O — доки не стане вузьким місцем CPU.
Швидкий план діагностики
Коли хтось каже «ZFS повільний», у вас є приблизно п’ять хвилин, щоб уникнути години здогадок. Ось порядок дій, що зазвичай дає результат.
Спочатку: вирішіть, чи вузьке місце — читання, записи або затримка від синхронних операцій
- Перевірте I/O пулу і затримки (чи диски насичені, чи операції чекають?).
- Перевірте, чи домінують sync-записи (NFS sync, database fsync).
- Перевірте, чи бачите ви промахи кеша або трешинг кешу.
Друге: перевірте тиск пам’яті і поведінку ARC
- Чи ОС свопиться або агресивно виконує reclaim?
- Чи ARC близький до свого максимуму і все ще має багато промахів?
- Чи ARC зменшується через тиск?
Третє: шукайте класичні фатальні налаштування
- Пул занадто заповнений, фрагментація і повільна топологія HDD vdev.
- Невірний recordsize для навантаження.
- Бекапи/scrub/resilver, що конфліктують з піковим навантаженням.
- Зловживання L2ARC (величезний SSD кеш при замалій ОЗП).
Четверте: і лише тоді говоріть про купівлю ОЗП
Якщо пул обмежений за IOPS і у вас стабільний гарячий набір, ARC допоможе. Якщо пул обмежений синхронними записами, виправляйте SLOG/топологію.
Якщо вузьке місце — CPU, виправляйте CPU. Якщо пул «заповнений до 92%», вирішуйте питання ємності.
Практичні завдання: команди, виводи та рішення
Це польові завдання. Вони не теоретичні. Запустіть їх, прочитайте виводи і прийміть рішення.
Команди припускають OpenZFS на Linux з типовими інструментами; підлаштуйте під ваш дистрибутив.
Завдання 1: Перевірте базовий тиск пам’яті (своп убиває продуктивність ZFS більше, ніж будь-яке налаштування ARC)
cr0x@server:~$ free -h
total used free shared buff/cache available
Mem: 125Gi 79Gi 3.2Gi 1.1Gi 42Gi 44Gi
Swap: 8.0Gi 2.6Gi 5.4Gi
Що це означає: Використовується своп. Це не обов’язково інцидент, але це запах проблеми.
Рішення: Якщо своп зростає під час навантаження або підвищення латентності, обмежте ARC і/або додайте ОЗП лише після підтвердження, що навантаження потребує кешування.
Завдання 2: Визначте, чи ядро треше під час reclaim
cr0x@server:~$ vmstat 1 5
procs -----------memory---------- ---swap-- -----io---- -system-- ------cpu-----
r b swpd free buff cache si so bi bo in cs us sy id wa st
3 0 270336 3421120 91264 41277440 0 0 120 250 5400 7200 12 6 78 4 0
5 1 270336 2897408 91264 41300224 0 64 90 1800 6100 9100 18 10 55 17 0
6 2 271360 2019328 91264 41311232 0 512 60 4200 6900 9800 15 11 42 32 0
Що це означає: so (swap out) зростає і wa (I/O wait) високий. Ви платите за тиск пам’яті затримкою дисків.
Рішення: Зменшіть c_max ARC (або виправте реального жера пам’яті) перед іншим втручанням. ZFS не може ефективно кешувати, коли ОС його витісняє.
Завдання 3: Підтвердіть розмір ARC і чи він прив’язаний до максимуму
cr0x@server:~$ arcstat 1 3
time read miss miss% dmis dm% pmis pm% mmis mm% arcsz c
12:01:10 820 96 11 12 1 84 10 0 0 88.2G 92.0G
12:01:11 901 210 23 18 2 192 21 0 0 88.3G 92.0G
12:01:12 870 245 28 20 2 225 26 0 0 88.3G 92.0G
Що це означає: Розмір ARC (arcsz) близький до цілі (c) і відсоток промахів зростає.
Рішення: Якщо це стабільний стан і навантаження читаюче, додавання ОЗП може допомогти. Якщо miss% зростає під час бекапів/сканів, спочатку виправте забруднення кешу.
Завдання 4: Подивіться докладний розподіл ARC (метадані vs дані)
cr0x@server:~$ cat /proc/spl/kstat/zfs/arcstats | egrep '^(size|c_max|c_min|hits|misses|mfu_hits|mru_hits|metadata_size|data_size) '
size 94701989888
c_min 4294967296
c_max 103079215104
hits 182993948
misses 23120291
mfu_hits 119002331
mru_hits 56211617
metadata_size 22811942912
data_size 70100215808
Що це означає: Ви кешуєте багато метаданих (~22 GB) і багато даних (~70 GB). Попадань значно більше за промахи в цілому.
Рішення: Якщо затримка все ще погана, можливо, проблема не в читальному кеші. Перейдіть до перевірки затримок пулу та синхронних записів.
Завдання 5: Перевірте стан пулу і очевидні обмеження розкладки vdev
cr0x@server:~$ zpool status -v
pool: tank
state: ONLINE
scan: scrub repaired 0B in 04:12:33 with 0 errors on Sun Dec 22 03:10:19 2025
config:
NAME STATE READ WRITE CKSUM
tank ONLINE 0 0 0
raidz2-0 ONLINE 0 0 0
sda ONLINE 0 0 0
sdb ONLINE 0 0 0
sdc ONLINE 0 0 0
sdd ONLINE 0 0 0
sde ONLINE 0 0 0
sdf ONLINE 0 0 0
errors: No known data errors
Що це означає: Один RAIDZ2 vdev поводиться як один vdev для IOPS. Чудово для ємності та послідовної пропускної здатності, але не для випадкових IOPS.
Рішення: Якщо навантаження — випадкове I/O (VM), не намагайтеся «закастомізуватися ARC». Додайте vdev, використовуйте дзеркала або перемістіть гарячі навантаження на SSD.
Завдання 6: Перевірте заповненість пулу (ефект падіння продуктивності реальний)
cr0x@server:~$ zfs list -o name,used,avail,refer,mountpoint tank
NAME USED AVAIL REFER MOUNTPOINT
tank 78.3T 4.1T 192K /tank
Що це означає: Пул фактично ~95% заповнений. Аліокація стає дорогою; фрагментація і поведінка metaslab погіршуються.
Рішення: Припиніть дебати про ARC. Додайте ємність або видаліть/мігруйте дані. Потім переоцініть продуктивність.
Завдання 7: Виявити тиск синхронних записів (пастка «чому мої записи повільні?»)
cr0x@server:~$ zfs get -o name,property,value -s local,received sync tank
NAME PROPERTY VALUE
tank sync standard
Що це означає: Поведінка sync — за замовчуванням. Застосунки, що викликають fsync, або клієнти, які вимагають sync, змушуватимуть поведінку ZIL.
Рішення: Якщо у вас база даних або NFS із синхронними записами — досліджуйте SLOG і затримки, а не розмір ARC.
Завдання 8: Перевірте, чи у вас є SLOG-пристрій і що це таке
cr0x@server:~$ zpool list -v tank
NAME SIZE ALLOC FREE CKPOINT EXPANDSZ FRAG CAP DEDUP HEALTH ALTROOT
tank 83.6T 78.3T 5.3T - - 41% 93% 1.00x ONLINE -
raidz2-0 83.6T 78.3T 5.3T - - 41% 93.6% - - -
Що це означає: Жодного лог-вневід не вказано. Синхронні записи потрапляють у основний пул.
Рішення: Якщо синхронна затримка записів — це біль, належний низькопучастковий SLOG (з захистом від втрати живлення) може допомогти більше, ніж будь-яке оновлення ОЗП.
Завдання 9: Виміряйте реальне I/O пулу і затримки в реальному часі
cr0x@server:~$ zpool iostat -v tank 1 3
capacity operations bandwidth
pool alloc free read write read write
---------- ----- ----- ----- ----- ----- -----
tank 78.3T 5.3T 1200 980 210M 145M
raidz2-0 78.3T 5.3T 1200 980 210M 145M
sda - - 210 160 35.0M 23.5M
sdb - - 195 165 33.1M 24.0M
sdc - - 205 155 34.2M 22.8M
sdd - - 180 170 30.8M 25.1M
sde - - 195 165 33.0M 24.0M
sdf - - 215 165 34.9M 23.9M
---------- ----- ----- ----- ----- ----- -----
Що це означає: Пул виконує багато операцій. Якщо це маленькі випадкові I/O на HDD, латентність ймовірно висока, навіть якщо пропускна здатність виглядає нормально.
Рішення: Якщо операцій багато і навантаження чутливе до затримки, розгляньте дзеркала/більше vdev/SSD-тіринг перед купівлею ОЗП.
Завдання 10: Перевірте властивості датасету, що безпосередньо впливають на ефективність ARC
cr0x@server:~$ zfs get -o name,property,value recordsize,compression,atime,primarycache tank/vmstore
NAME PROPERTY VALUE
tank/vmstore recordsize 128K
tank/vmstore compression lz4
tank/vmstore atime on
tank/vmstore primarycache all
Що це означає: 128K recordsize і atime=on для сховища VM — типовий самосаботаж. atime-оновлення додають навантаження на запис; великі записи збільшують випадкове I/O.
Рішення: Розгляньте atime=off і recordsize, придатний для VM (часто 16K) після тестування. Якщо гарячий набір малий — ARC теж працюватиме краще.
Завдання 11: Подивіться, чи компресія допомагає або шкодить (і чи CPU — справжній вузький вузол)
cr0x@server:~$ zfs get -o name,property,value compressratio tank/vmstore
NAME PROPERTY VALUE
tank/vmstore compressratio 1.62x
Що це означає: Компресія ефективна: 1.62x означає, що ви заощаджуєте I/O і вміщуєте більше логічних даних в ARC.
Рішення: Залишайте її, якщо CPU не завантажений. Якщо CPU насилу справляється, компресія може стати вузьким місцем і додаткова ОЗП не вирішить проблему.
Завдання 12: Перевірте завантаження CPU під час скарг на «повільне сховище»
cr0x@server:~$ mpstat -P ALL 1 2
Linux 6.8.0 (server) 12/26/2025 _x86_64_ (32 CPU)
12:05:01 PM CPU %usr %nice %sys %iowait %irq %soft %steal %guest %gnice %idle
12:05:02 PM all 58.2 0.0 18.9 1.1 0.0 0.8 0.0 0.0 0.0 21.0
12:05:02 PM 7 96.0 0.0 3.8 0.0 0.0 0.0 0.0 0.0 0.0 0.2
Що це означає: Один CPU майже на максимумі. Це може бути однопотоковий процес (контрольні суми, компресія, VM, шлях переривань).
Рішення: Якщо затримки зберігання корелюють із завантаженням CPU, додавання ARC не допоможе. Досліджуйте «гарячі точки» CPU і розподіл навантаження.
Завдання 13: Перевірте наявність L2ARC і чи він розумний для вашої ОЗП
cr0x@server:~$ zpool status tank | egrep -A3 'cache|special|logs'
cache
nvme1n1p1 ONLINE 0 0 0
Що це означає: У вас є пристрій L2ARC. L2ARC не магічний; він споживає ARC-метадані і може збільшувати ампліфікацію читань.
Рішення: Якщо ОЗП мала, а L2ARC велика, ви можете стати повільнішими. Перевірте статистику ARC/L2ARC перед тим, як вважати, що це допомагає.
Завдання 14: Перевірте, чи ARC домінує метаданими (підказка, що метадані — ціль)
cr0x@server:~$ arc_summary | egrep 'ARC Size|Most Recently Used|Most Frequently Used|Metadata Size|Data Size'
ARC Size: 88.3 GiB
Most Recently Used Cache Size: 31.2 GiB
Most Frequently Used Cache Size: 56.1 GiB
Metadata Size: 21.3 GiB
Data Size: 65.8 GiB
Що це означає: Значна частина — метадані. Це корисно, коли ваше навантаження — «багато файлів», снапшоти і перебір директорій.
Рішення: Якщо метадані — болючі, і ви на HDD, розгляньте special vdev для метаданих перед тим, як нескінченно додавати ОЗП.
Завдання 15: Знайдіть джерела забруднення кешу (послідовні читачі, що вирівнюють ARC)
cr0x@server:~$ iotop -oPa
Total DISK READ: 422.31 M/s | Total DISK WRITE: 12.05 M/s
PID PRIO USER DISK READ DISK WRITE SWAPIN IO> COMMAND
18322 be/4 backup 410.12 M/s 0.00 B/s 0.00 % 92.14 % tar -cf - /tank/vmstore | ...
Що це означає: Робота бекапу стрімить читання. Це може витісняти корисний вміст кешу, якщо не керувати.
Рішення: Розгляньте встановлення primarycache=metadata на бекапних датасетах, використання snapshot send/receive патернів або планування/лімітування I/O бекапу.
Завдання 16: Підтвердіть ваш ліміт ARC і безпечно відрегулюйте (тимчасовий тест)
cr0x@server:~$ cat /sys/module/zfs/parameters/zfs_arc_max
103079215104
cr0x@server:~$ echo 68719476736 | sudo tee /sys/module/zfs/parameters/zfs_arc_max
68719476736
Що це означає: Ви зменшили ARC max до 64 GiB (значення в байтах). Це жива зміна в багатьох налаштуваннях.
Рішення: Якщо затримка застосунку покращується (менше свопу, менше reclaim), залиште нижчий кап. Якщо читальна латентність погіршилась і тиск пам’яті в нормі — додавайте ОЗП.
Жарт №2: L2ARC — як друга морозилка: корисна, доки ви не зрозумієте, що купили її, бо забули, як працюють продукти.
Три корпоратівні міні-історії (як це йде не так у реальному житті)
Міні-історія 1: Інцидент через хибне припущення («ОЗП на ТБ» як технічна вимога)
Середня компанія оновила свої вузли зберігання для приватного хмарного середовища. У RFP буквально вказали пам’ять як «1 ГБ на ТБ usable».
Ніхто не кинув виклик, бо це звучало технічно і мало число. Закупівля любить числа.
Нові вузли приїхали з великою кількістю дисків і пристойною кількістю ОЗП — за правилом по терабайтах. Проблема: навантаження було VM,
переважно випадкові читання й записи, розміщені на парі великих RAIDZ2 vdev на вузол. Гарячий робочий набір був малим і спайковим, а реальним лімітером
були випадкові write IOPS і затримка під час snapshot-штормів.
Через тиждень з’явилось багато тикетів: «VM зависають», «таймаути бази даних», «графіки сховища виглядають нормально». Графіки виглядали нормально, бо це були графіки пропускної здатності.
Латентність була вбивцею, і ZFS робив саме те, що ви очікуєте: він не може витягти IOPS з паритетного RAIDZ під випадковим навантаженням.
Постмортем був неприємним. Більше ОЗП трохи допомогло б читанням. Але інцидент спричинили затримки записів і топологія vdev.
Виправлення не було «подвоїти пам’ять». Воно полягало в «припинити розміщувати випадкові VM навантаження на невелику кількість широких RAIDZ vdev» і «розділити навантаження за класом продуктивності».
Урок: правило підбору, що ігнорує IOPS, — ризик. «ОЗП на ТБ» мовчить про те, що найчастіше б’є першим.
Міні-історія 2: Оптимізація, яка призвела до погіршення (L2ARC скрізь, бо SSD дешеві)
Інша команда експлуатувала флот вузлів з ZFS для віртуалізації. Хтось порахував: NVMe недорогі, тож додамо L2ARC на кожен вузол. Більше кешу — швидші читання.
Зміна пройшла з гарним Jira-звідом і нульовими вимірюваннями.
Через кілька днів під навантаженням читальна латентність погіршилася. Не катастрофічно, але достатньо, щоб дратувати клієнтів і спричиняти періодичні збої.
Команда звинуватила мережу, потім гіпервізор, потім «накладні витрати ZFS».
Насправді все було передбачувано: вузлів було замало ОЗП, щоб підтримувати L2ARC ефективно. L2ARC споживає ресурси ARC для заголовків і метаданих,
і змінює I/O-патерни. Пристрої кешу були великі відносно ОЗП, що збільшувало чурн і накладні, при цьому не утримуючи потрібні гарячі дані.
Під змішаним навантаженням вони платили додаткову роботу за промахи.
Відкат L2ARC на деяких вузлах покращив стабільність миттєво. Пізніше їх повторно ввели на вузлах з достатньою ОЗП і на навантаженнях з підтвердженою локальністю читань.
Урок: «SSD кеш» не завжди добре. Якщо ви не знаєте типи промахів і робочий набір, ви просто додаєте ще одну рухому частину, що може підвести у нерідкий час.
Міні-історія 3: Нудна, але правильна практика, яка врятувала ситуацію (cap ARC + дисципліна змін)
Команда обслуговувала файловий сервіс на ZFS для внутрішніх збірок і артефактів. Під час активного релізу сервіс почав таймаутити.
Перший респондент помітив активність свопу і шторм реклейму. Класика.
У них був нудний рукбук: «Перевірити тиск пам’яті; тимчасово обмежити ARC; валідувати відновлення застосунків; потім налаштувати остаточно.»
Жодної героїки, жодного перегляду форумів. Вони зменшили zfs_arc_max у живому середовищі, звільнивши пам’ять для сервісів, що фактично відмовлялися.
Латентність впала за кілька хвилин. Не тому, що ARC був поганим, а тому, що система змістилася: нові агенти, більше контейнерів і більший обсяг збірок з’їдали пам’ять.
ARC робив свою роботу — використовував доступну пам’ять — поки ОС не почала свопити.
Постійне виправлення не було «вимкнути ARC». Це було встановлення розумного капа ARC, збільшення ОЗП у наступному циклі апаратного забезпечення і додавання моніторингу,
що сигналізував би про своп і події зменшення ARC. Сервіс пережив реліз без нового інциденту.
Урок: нудні запобіжні заходи краще за хитрі припущення. ARC потужний, але він ніколи не повинен голодувати вашу бізнес-логіку.
Поширені помилки: симптом → корінь проблеми → виправлення
1) «ZFS повільний після додавання дисків»
Симптом: Більше ємності, гірша латентність; графіки пропускної здатності виглядають нормально.
Корінь: Нова розкладка vdev збільшила накладні на паритет або розширила RAIDZ без додавання IOPS; фрагментація погіршилась; пул став занадто заповненим.
Виправлення: Перевірте zpool iostat і заповненість пулу; додавайте vdev (IOPS), а не просто диски (ємність). Тримайте використання пулу під контролем.
2) «ARC hit ratio високий, але застосунки все ще таймаутять»
Симптом: Відсоток попадань ARC виглядає пристойно; спалахи латентності зберігаються.
Корінь: Латентність синхронних записів (ZIL/SLOG), завантаження CPU або повільний окремий vdev; ARC не виправляє синхронну семантику записів.
Виправлення: Виміряйте поведінку sync; перевірте SLOG; перевірте CPU і латентність по vdev. Вирішуйте фактичне вузьке місце.
3) «Ми додали L2ARC і все стало гірше»
Симптом: Вища латентність читання і більше джиттера після додавання SSD кешів.
Корінь: L2ARC занадто великий відносно ОЗП; збільшені накладні; чурн кешу; невідповідне навантаження (відсутня локальність).
Виправлення: Видаліть або зменшіть L2ARC; забезпечте достатню ОЗП; підтвердіть вигоду статистикою промахів перед повторним введенням.
4) «VM зависають під час бекапів»
Симптом: Передбачувані падіння продуктивності під час вікон бекапу.
Корінь: Послідовні читання забруднюють ARC і конкурують за диск; scrub/resilver перетинаються з продуктивним I/O.
Виправлення: Обмежте I/O бекапу, розділіть датасети, використовуйте primarycache=metadata де доречно, плануйте scrub уважно.
5) «У нас багато ОЗП; чому ARC не величезний?»
Симптом: Розмір ARC здається обмеженим або меншим, ніж очікували.
Корінь: zfs_arc_max встановлено навмисно або за замовчуванням дистро; тиск пам’яті; ліміти контейнера; взаємодія з hugepages.
Виправлення: Перевірте параметри ARC і доступність пам’яті; змінюйте ліміти свідомо; не голодуйте ОС.
6) «Операції з маленькими файлами повільні на HDD пулі»
Симптом: Лістинги директорій, розпакування архівів, git-операції болючі.
Корінь: Метадані шукають по HDD; недостатнє кешування метаданих; відсутній special vdev.
Виправлення: Забезпечте адекватну ОЗП для метаданих; розгляньте special vdev для метаданих/малих блоків; перевірте по поведінці метаданих у ARC.
7) «Продуктивність падає, коли пул майже повний»
Симптом: Було нормально на 60%, жахливо на 90%.
Корінь: Витрати на алокацію і фрагментація; metaslab-обмеження; записова ампліфікація RAIDZ посилюється.
Виправлення: Додайте ємність, мігруйте дані, застосуйте квоти/резервування. Не вважайте 95% заповненим нормальним станом.
8) «Ми налаштували recordsize і тепер випадкові читання гірші»
Симптом: Латентність зросла після зміни властивостей датасету.
Корінь: recordsize не підходить навантаженню; змінився I/O-патерн і поведінка кешу; невідповідність розміру блоків застосунку.
Виправлення: Використовуйте recordsize, придатний для конкретного датасету; тестуйте з репрезентативним навантаженням; не змінюйте глобально в паніці.
Чеклісти / покроковий план
План A: Ви купуєте обладнання і хочете підібрати ОЗП без релігії
- Запишіть навантаження. VM? NFS домашні каталоги? Об’єктне сховище? БД? Змішане?
- Оберіть дві метрики, що мають значення. Наприклад: p95 читальної латентності і p95 синхронної латентності запису.
- Вирішіть гіпотезу гарячого набору. «Ми думаємо, що 200 GB читається повторно під час робочих годин.» Поставте число.
- Виберіть консервативний базовий обсяг ОЗП. Залиште місце для ОС/застосунків; плануйте обмежити ARC.
- Оберіть топологію пулу з пріоритетом IOPS. Дзеркала і більше vdev перемагають широкі RAIDZ для випадкових навантажень.
- Розв’яжіть, чи потрібне прискорення метаданих. Якщо так, розгляньте special vdevs (з відмовостійкістю), а не нескінченну ОЗП.
- Заплануйте спостережуваність. Статистика ARC, латентність, своп, CPU і метрики по vdev з першого дня.
- Запустіть навантажувальне тестування, що нагадує продакшн. Якщо не можете — визнайте, що гадаєте, і побудуйте додатковий запас безпеки.
План B: Продакшн повільний і вам потрібен фікс з мінімальним ризиком
- Перевірте своп і reclaim. Якщо своп, обмежте ARC і стабілізуйте систему.
- Перевірте заповненість пулу. Якщо небезпечно заповнено — зупиніться і вирішіть ємність. Усе інше — косметика.
- Перевірте латентність і поведінку sync. Визначте, чи читання чи записи — біль.
- Виявте забруднення кешу. Бекапи і скани — часті винуватці.
- Лише потім налаштовуйте властивості датасету. Робіть це по датасетах з нотатками щодо відкату.
- Переоцініть з тими ж метриками. Якщо ви не виміряли до змін — виміряйте після і не прикидайте, що довели щось.
План C: Ви підозрюєте, що у вас замало ОЗП для ARC (і хочете докази)
- Підтвердіть, що ARC під час нормального навантаження близький до максимуму.
- Підтвердіть, що miss% залишається підвищеним у період повільності.
- Підтвердіть, що навантаження читаюче і має локальність. Випадкові читання, що повторно потрапляють у той самий робочий набір, а не скан.
- Підтвердіть, що диски — вузьке місце на промахах. Якщо SSD уже швидкі, вигода ARC може бути маргінальною.
- Додайте ОЗП або перерасподіліть пам’ять і протестуйте знову. Покращення має бути видно в p95 латентності, а не лише «відчуттях».
ЧаПи
1) Скільки ОЗП мені потрібно для ZFS?
Достатньо, щоб запускати ваше навантаження без свопінгу, плюс стільки ARC, щоб суттєво зменшити дорогі читання. Почніть з розумного базового рівня (16–64 GB залежно від ролі),
вимірюйте промахи ARC і латентність, потім масштабуйтесь по ОЗП лише якщо це зменшує вузьке місце.
2) Чи колись корисне правило «1 ГБ ОЗП на ТБ»?
Як застереження, що «великі пули з метаданегенними навантаженнями на повільних дисках потребують пам’яті», — так. Як специфіка купівлі — ні.
Воно ігнорує IOPS, навантаження, налаштування датасетів і факт існування холодних даних.
3) Чи більше ARC завжди покращує продуктивність?
Ні. Якщо ви обмежені латентністю записів, CPU, топологією або потерпаєте від забруднення кешу, більше ARC може нічого не дати або погіршити ситуацію через тиск пам’яті.
4) Чи варто обмежувати ARC?
На серверах зі змішаним використанням (гіпервізори, хости контейнерів, машини з базами даних) — так, обмежуйте його навмисно.
На виділених аплайянсах зберігання можна дозволити рости, але все одно перевіряйте поведінку під навантаженням і після перезавантажень.
5) Який відсоток попадань ARC є «добрим»?
«Добре» — коли латентність застосунку відповідає цілі. Відсоток попадань контекстний. Стрімінгове навантаження може мати низький hit% і все одно бути в порядку.
Навантаження VM з низьким hit% і великою випадковою латентністю відчуватиметься жахливо.
6) Коли має сенс L2ARC?
Коли ваш робочий набір більший за ОЗП, але все ще має локальність, і ваші диски достатньо повільні, щоб SSD-попадання мали значення.
Також коли у вас достатньо ОЗП, щоб його «кормити». L2ARC — не пластир для поганої топології пулу.
7) Чи «пам’ятьожерний» ZFS порівняно з іншими файловими системами?
ZFS охоче використовує доступну пам’ять для ARC, бо це корисно. Це може виглядати як «великі витрати» в панелі моніторингу.
Питання не в «великий ARC» — а в тому, чи система стабільна і чи латентність покращується.
8) Чи змінює компресія потреби в ОЗП?
Часто так — у хорошому сенсі. Компресія може збільшити ефективну ємність ARC, бо більше логічних даних поміщається на байт кешу, і зменшити I/O.
Але якщо CPU стає вузьким місцем, ви просто перенесли пробку.
9) А як щодо дедуплікації?
Використовуйте її тільки якщо можете довести збереження і розумієте пам’яттєві й продуктивні наслідки для вашої версії і навантаження.
Якщо вмикаєте dedup без плану — ви підписуєтесь на інцидент.
10) Чому продуктивність змінюється після перезавантаження?
ARC стартує «холодним». Якщо ваша продуктивність залежить від прогрітого кешу, після перезавантаження буде період сповільнення.
Це нормальна поведінка кешу. Вирішіть це достатньою ОЗП, дизайном з урахуванням навантаження і уникайте залежності критичних шляхів від теплого кешу.
Наступні кроки, які ви реально можете зробити цього тижня
Якщо ви хочете захищене рішення щодо розміру ARC — таке, що не висміють на рев’ю — зробіть це в такому порядку:
- Пробазуйте систему: зберіть
free -h,vmstat, статистику ARC іzpool iostatпід час періоду повільності. - Розділіть проблему: вирішіть, чи ви обмежені по читанню, запису чи синхронній латентності. Не гадайте.
- Приберіть очевидні самошкоди: виправте заповненість пулу, припиніть свопінг і не дозволяйте бекапам знищувати ваш кеш.
- Налаштуйте по датасетах: узгодьте
recordsize,primarycacheіatimeз навантаженням. - Лише потім купуйте ОЗП: якщо промахи залишаються високими при сталому локальному робочому наборі і диски — вузьке місце, додайте ОЗП і перевірте покращення тими ж метриками.
Якщо хтось наполягає на «ОЗП на ТБ», задайте їм одне питання: «Яке навантаження і яка ціль по затримці?» Якщо вони не можуть відповісти — вони не підбирають, а читають напам’ять.