heaptrack/

Рассмотрим типичную задачу. Есть программа на C или C++ с исходниками. Известно, что при выполнении определенных условий программа начинает отжирать слишком много памяти. Нужно понять, почему это происходит, и по возможности исправить. Инструменты, которые мы рассматривали до этого, например, в заметке Профилирование кода на C/C++ в Linux и FreeBSD , для этого явно не подходят. Спрашивается, что же тогда делать? На помощь приходит Heaptrack!

Примечание: Heaptrack является аналогом Valgrind Massif , только, в отличие от него, работает намного быстрее. См также заметку Поиск ошибок работы с памятью в C/C++ при помощи Valgrind .

Для установки Heaptrack я воспользовался этим AUR (см заметку Управление пакетами в Arch Linux с помощью ABS и pacman ). Также нам понадобятся Massif Visualizer и его зависимость KDiagram , которые также доступны в AUR. Если вы используете дистрибутив, отличный от Arch Linux, уверен, для него в каком-то виде данные пакеты тоже есть. В крайнем случае, можно посмотреть файлы PKGBUILD у Арча и собрать все из исходников таким же образом. Насколько мне известно, в настоящее время Heaptrack работает только под Linux. Поэтому, если вы используете другую ОС… ну что ж, хреново быть вами 🙂

Пользоваться Heaptrack очень просто. Для примера натравим его на программку из Не унылого поста о списках и деревьях поиска в языке C :

heaptrack . / test_rbtree
# или: heaptrack -p PID

heaptrack_print —print-leaks
—print-histogram histogram.data
—print-massif massif.data
—print-flamegraph flamegraph.data
—file . / heaptrack.test_rbtree.22023.gz > report.txt

Ключ --print-leaks включает вывод информации о потенциальных утечках памяти (отключено по умолчанию), --print-histogram включает запись статистики по размерам выделенной памяти, а --print-massif создает файл, пригодный для просмотра в Massif Visualizer. Что делат ключ --print-flamegraph попробуйте угадать сами 🙂 Файл flamegraph.data будет использован чуть ниже.

Полный пример отчета можно посмотреть здесь . Наиболее интересная его часть:

PEAK MEMORY CONSUMERS

4.98MB peak memory consumed over 31111 calls from
tree_allocfunc
at /home/eax/projects/c/c-algorithms/test/struct/test_rbtree.c:37
in /home/eax/projects/c/c-algorithms/build/test/struct/test_rbtree
1.24MB consumed over 7777 calls from:
rb_insert
in /home/eax/projects/c/c-algorithms/build/test/struct/test_rbtree
left_right_walk_test
at /home/eax/projects/c/c-algorithms/test/struct/test_rbtree.c:166
in /home/eax/projects/c/c-algorithms/build/test/struct/test_rbtree
run_tests
at /home/eax/projects/c/c-algorithms/test/struct/test_rbtree.c:430
in /home/eax/projects/c/c-algorithms/build/test/struct/test_rbtree
main
at /home/eax/projects/c/c-algorithms/test/struct/test_rbtree.c:458
in /home/eax/projects/c/c-algorithms/build/test/struct/test_rbtree

Вполне похоже на правду! Действительно, почти вся память должна выделяться во время вставки в RB-дерево.

Если текстовый отчет вам не кажется слишком наглядным, попробуйте запустить Massif Visualizer:

massif-visualizer massif.data

Выглядит он приблизительно так (кликабельно, PNG 1366 x 747, 224 Кб):

Massif Visualizer

Кроме того, можно построить флеймграф:

git clone https: // github.com / brendangregg / FlameGraph
. / FlameGraph / flamegraph.pl flamegraph.data > flamegraph.svg

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

Собственно, это все! А чем вы профилируете использование оперативной памяти?

EnglishRussianUkrainian