CodeFest 2018. Михаил Ярийчук (Hibernating Rhinos) — Garbage Collector — друг или враг?

CodeFest 2018. Михаил Ярийчук (Hibernating Rhinos) — Garbage Collector — друг или враг?

Посмотрите выступление Михаила: https://2018.codefest.ru/lecture/1244/

Сборщик мусора в .Net это замечательная штука, позволяющая разработчикам быстрее писать код, не отвлекаясь на порой весьма замысловатое управление памятью.

Но иногда, сборка мусора может стать не такой уж замечательной, заставляя программу виснуть на длительное время, доходящее до абсурдных 90% от времени исполнения (или выше!)

Что-же делать?
В своем докладе, я расскажу о сборщике мусора в .Net, как он влияет на производительность и что можно сделать для сокращения количества провисаний и увеличения скорости работы программ.

Уровень: некоторе знание/опыт разработки на .Net, Java. Разработчики, технические менеджеры.

16b6c87229eaf58768d25ed7b2bbbf52?s=128

CodeFest

April 09, 2018
Tweet

Transcript

  1. Garbage Collector - друг или враг? Михаил Ярийчук • Wizard

    Apprentice • Software Developer Hibernating Rhinos
  2. Here be dragons… https://pixabay.com/en/map-of-the-world-old-historically-2241469/

  3. Garbage Collector : Лучший друг программиста • Эффективность à не

    нужно вручную контролировать память • Стабильность à нет утечек памяти, нет buffer overflow https://www.flickr.com/photos/oakleyoriginals/3526895658
  4. Garbage Collector : Худший враг программиста

  5. Garbage Collector : Худший враг программиста

  6. None
  7. Managed Heap • Аллокатор • Внутри “managed heap” сложность резервации

    памяти О(1) • Больше памяти для программного процесса à увеличивает “managed heap” • Сборщик Мусора • Подбирает ненужную память à “мусор”
  8. Gen 0 Gen 1 Gen 2 LOH Как устроен managed

    heap?
  9. Когда запускается GC? • Бюджет резерваций памяти • Kоличествo обьектов

    которые остаюся после GC (чем больше выживет, тем больше бюджет резерваций) • Фрагментированность различных поколений
  10. Простые оптимизации • Как можно меньше резерваций памяти • Долго-живущие

    обьекты эффективнее коротко-живущих • Generic и синхронные коллекции не эффективны • ArraySegment<T>, StringSegment<T>, Span<T> • Кэширование, Объектный пул
  11. Простые оптимизации - Span<T>

  12. В общем… Чем меньше работы для GC, тем больше эффективность

  13. None
  14. 50 3 оттенка памяти в .Net Managed Heap Stack Memory

    Unmanaged Heap
  15. Stack memory • Эффективно резервирует и освобождает память • Не

    приводит к GC • Предназначена для коротко-живущих объектов • Предназначена для небольших объектов (иначе StackOverflowExceptions) • Только для простых типов (Primitives)
  16. Stack memory

  17. Stack memory – самый распространенный статус 1 Heap Heap Heap

    Heap
  18. Stack memory – самый распространенный статус 2 Heap

  19. Stack memory – самый распространенный статус 3 Stack memory

  20. Stack memory – самый распространенный статус GC циклы за 1k

    операций
  21. Unmanaged Heap • Детерминистичная резервация и освобождение à не зависит

    от GC • Возможность подогнать алгоритмы аллокаторов к специфическим задачам
  22. Перевернуть строку 1 Heap Heap Heap

  23. Перевернуть строку 2 Heap Heap

  24. Перевернуть строку 3 Heap

  25. Unmanaged Heap – Перевернуть строку GC циклы за 1k операций

  26. Все это замечательно, но как работать с Unmanaged Memory? Oсторожно!

  27. Во первых, Span<T> и Memory<T>

  28. Во вторых, Memory Allocators

  29. Memory Allocator • Алгоритм контролирующий резервацию и освобождение памяти •

    Сложность резервации и освобождения не всегда тривиальна
  30. Memory Allocator • Стратегия резерваций памяти • Сложность (complexity) •

    “one size fits all” – большая ошибка
  31. Свободные Сегменты Монотонный Аллокатор Сегмент 1 64KB Сегмент 2 64KB

    Сегмент 3 64KB Сегмент 4 64KB Сегмент 5 64KB Указатель на следующий свободный сегмент Зарезервированные Сегменты
  32. Аллокатор - Multipool 2^0 à1K 2^1 à 2K 2^2 à

    4K 2^3 à 8K 2^4 à 16K
  33. Memory Allocator – Вариация Multipool (Buddy System) 256KB 128KB 64KB

    64KB 128KB 64KB 64KB Сегмент 1 64KB Сегмент 2 64KB Сегмент 3 64KB Сегмент 4 64KB
  34. Multipool (Buddy System) – резервация памяти 256KB 128KB 64KB 64KB

    128KB 64KB 64KB Сегмент 1 64KB Сегмент 2 64KB Сегмент 3 64KB Сегмент 4 64KB Резервируем сегмент Пометим как частично зарезервированный
  35. Multipool (Buddy System) – освобождение памяти 256KB 128KB 64KB 64KB

    128KB 64KB 64KB Сегмент 1 64KB Сегмент 2 64KB Сегмент 3 64KB Сегмент 4 64KB Свободный Сегмент? Освобождаем сегмент
  36. На что обращать внимание • Сложность резервации и освобождения памяти

    • Многопоточность • Длительность операций • Плотность (частота) резерваций • Вариации величин сегментов
  37. Некоторые известные аллокаторы • TCMalloc à http://goog-perftools.sourceforge.net/doc/tcmalloc.html • Hoard à

    https://github.com/emeryberger/Hoard • Jemalloc.NET à https://github.com/allisterb/jemalloc.NET • Специализированные à https://github.com/mtrebi/memory-allocators
  38. Правильных ответов не существует!

  39. А теперь...

  40. Тест на производительность RavenDB 4.0 RC (build 40019) • Managed

    Heap • Unmanaged memory • Сериализация/Десериализация • Манипуляции со строками RavenDB 3.5.5 (build 35223) • Только Managed Heap Загружаем 1,000,000 документов в базу данных CPU: i7-4770 Памаять: 16GB Диск: SSD
  41. Результаты Managed Heap и Unmanaged Только Managed Heap

  42. Результаты Managed Heap и Unmanaged Только Managed Heap

  43. Результаты Managed Heap и Unmanaged Только Managed Heap

  44. Больше сложность à больше багов

  45. Баги? Какие баги? • Fail fast, fail often • Аллокатор

    Electric Fence • Reference counting + finalizers • Старый добрый printf debugging • Сохранять StackTrace в важных точках
  46. Подытожим • GC может ухудшить производительность • Stack Memory à

    Полезная штука. Иногда. • Unmanaged memory – не так уж и страшно • Unmanaged memory à меньше циклов GC • Не стоит использовать LINQ в критическом коде
  47. @myarichuk Вопросы? michael.yarichuk@hibernatingrhinos.com Михаил Ярийчук • Wizard Apprentice • Software

    Developer Hibernating Rhinos https://github.com/ravendb/ravendb/tree/v4.0/src/Sparrow