Виртуальная память и
большие страницы
Константин Новаковский
Selectel
Почему мы думаем о памяти
6 датацентров (6,5к м2)
Аренда серверов / стоек / серверных помещений / волокон
Виртуальное приватное облако
Облачное хранилище / CDN
Мониторинг
Vscale
Anycast DNS
Чуть-чуть истории
Intel® 80386 (1985 год)
Защищенный режим
Виртуальная память
MMU
https://en.wikipedia.org/wiki/Intel_80386
Virtual to Physical memory translation
Почти наши дни
Размер Page Tables сервера с 12Гб ОЗУ и ядром 2.6.32:
cat /proc/meminfo | grep PageTables
119792 kB = 116 mB
Наши дни
Размер Page Tables сервера с 396Гб ОЗУ и ядром 4.4:
cat /proc/meminfo | grep PageTables:
226788 kB = 221 mB
Enlarge your Pages!
TLB разделён на несколько частей в зависимости от архитектуры:
• 4KB страницы
• 2MB страницы
• 1GB страницы
• нет предела совершенству
TLB miss обрабатывается быстрее (-1 уровень)
Посмотри на мои TLB
cpuid | grep -i 'tlb.*entries'
instruction TLB: 4K, 8-way, 64 entries
instruction TLB: 2M/4M pages, fully, 8 entries
data TLB: 4K pages, 4-way, 64 entries
data TLB: 1G pages, 4-way, 4 entries
L2 TLB: 4K/2M pages, 8-way, 1024 entries
Как использовать?
hugetlbpage - “Pure” Huge Pages
khugepaged - Transparent Huge Pages
hugetlbpage - “Pure” Huge Pages
sysctl vm.nr_hugepages=170000
или
echo 170000 > /proc/sys/vm/nr_hugepages
или
kernel boot param: /vmlinuz hugepages=170000 !
170000 * 2048 kB = 340000 mB = 332 gB
perf stat 
-e iTLB-load-misses,iTLB-loads,dTLB-load-misses,dTLB-loads 
-a -p <pid> -- sleep 10
perf
Without Huge Pages
10,969 iTLB-load-misses
5,945,847 iTLB-loads
26,007 dTLB-load-misses
3,815,595 dTLB-loads
Huge Pages
6,614 iTLB-load-misses
4,301,442 iTLB-loads
13,199 dTLB-load-misses
1,792,403 dTLB-loads
libhugetlbfs
Позволяет использовать большие страницы через LD_PRELOAD
Устарел
Transparent Huge Pages
Может включаться автоматически
Умеют свопится
Действительно прозрачно
Накладные ресурсы по обслуживанию - khugepaged
ДА - НЕ ЗНАЮ - НЕТ
/sys/kernel/mm/transparent_hugepage/enabled:
[always] [madvise] never
Отключить и не использовать
Использовать при явном запросе
Always :)
Non posix madvise call
int madvise(void *addr,
size_t length,
int advice);
advices:
MADV_HUGEPAGE
MADV_NOHUGEPAGE
Transparent Huge Pages
echo madvise > /sys/kernel/mm/transparent_hugepage/enabled
Минусы: отваливаются THP для большинства приложений
Плюсы: утечка памяти перестаёт нас так беспокоить
Ручки khugepaged
alloc_sleep_millisecs 60000
pages_collapsed
full_scans
max_ptes_none
max_ptes_swap
grep ^thp /proc/vmstat (4.4)
thp_fault_alloc 43670
thp_fault_fallback 11685
thp_collapse_alloc 7899
thp_collapse_alloc_failed 2272
thp_split 2935
thp_zero_page_alloc 3
thp_zero_page_alloc_failed 0
И всё сразу быстро и шелковисто?
не все альтернативные аллокаторы научились THP
https://github.com/jemalloc/jemalloc/issues/243
Приложения
Те кто не научились использовать “нативные” HP:
отключить THP если есть “просадка” производительности
Те кто научились (Oracle, Postgresql, Mysql, etc):
отключить THP
echo N > /sys/kernel/mm/nr_hugepages
TOP по большим страницам
не существует TOP-like инструментов для отслеживания HP
grep … /proc/<pid>/smaps
7f01d4c8d000-7f01dc000000 rw-p 00000000 00:00 0
Size: 118220 kB
Rss: 116752 kB
Pss: 116752 kB
...
Private_Dirty: 116752 kB
Referenced: 116752 kB
Anonymous: 116752 kB
AnonHugePages: 116736 kB
Private_Hugetlb: 0 kB
KernelPageSize: 4 kB
MMUPageSize: 4 kB
VmFlags: rd wr mr mw me ac sd
Transparent
Huge Pages
7f01e3e00000-7f0203e00000 rw-p 00000000 00:25 1760066
Size: 524288 kB
Rss: 0 kB
Pss: 0 kB
...
Private_Dirty: 0 kB
Referenced: 0 kB
Anonymous: 0 kB
AnonHugePages: 0 kB
Private_Hugetlb: 524288 kB
KernelPageSize: 2048 kB
MMUPageSize: 2048 kB
VmFlags: rd wr mr mw me dc de ht sd
Huge
Pages
HugeTLB
Не уходит в swap
Уменьшает расходы ядра на обслуживание PageTable
Приложение должно заботиться об этом
Память зарезервирована и недоступна большинству приложений
THP
Может уходить в swap
Увеличивает расходы ядра на обслуживание
Не все приложения готовы к такому повороту
Контейнеры?
Что почитать?
https://linux-mm.org/
https://www.kernel.org/doc/Documentation/vm/
https://www.kernel.org/doc/Documentation/vm/hugetlbpage.txt
https://www.kernel.org/doc/Documentation/vm/transhuge.txt
Intel® 64 and IA-32 Architectures Software Developer’s Manual
https://www.kernel.org/doc/gorman/html/understand/understand006.html
Вопросы?

Погружение в виртуальную память и большие страницы / Константин Новаковский (Selectel)

Editor's Notes

  • #3 Сразу об экономике и 200р за виртуалку с 512мб. Захерачим на 256гб столько-то виртуалок.
  • #4 Не помешало бы добавить слайд с определениями основных понятий; Когда будешь излагать историю, скажи пару слов про HugePages - когда, в какой версии ядра они появились
  • #5 https://en.wikipedia.org/wiki/Intel_80386
  • #7 TODO: добавить L1, L2, L3 caches
  • #9 Упомянуть про тариф в 512мб, при 396 ГБ - 4гб на pagetables
  • #10 Упомянуть про тариф в 512мб, при 396 ГБ - 4гб на pagetables
  • #14 system wide THP since 2.6.38, but was slow, improved in 3.11
  • #22 можно какой-нибудь пример кода, где этот системный вызов используется Сильно сократить
  • #23 Slab: 1999040 kB
  • #33 что с OOM