Valgrind утверждает, что есть несвободная память. Это плохо? - PullRequest
3 голосов
/ 27 января 2010

Valgrind дает мне следующую сводку утечки в моем коде. Тем не менее, я освободил всю память malloc'а. Это плохо или это нормально? Моя программа на c.

== 3513 == РЕЗЮМЕ УТЕЧКИ:

== 3513 == определенно потеряно: 0 байтов в 0 блоках.

== 3513 == возможно потеряно: 0 байтов в 0 блоках.

== 3513 == все еще достижимо: 568 байтов в 1 блоке.

== 3513 == подавлено: 0 байтов в 0 блоках.

Ответы [ 7 ]

7 голосов
/ 27 января 2010

Сообщение valgrind still reachable: 568 bytes in 1 blocks. означает, что в вашем приложении была освобождена память, которая все еще «достижима», что означает, что у вас еще есть указатель на нее где-то. При выключении это, вероятно, означает какую-то глобальную переменную. Тем не менее, поскольку число байтов, «определенно просочившихся» или «вероятно просочившихся», равно нулю, это условие является полностью благоприятным. Не беспокойся об этом.

6 голосов
/ 27 января 2010

Доступная память означает, что на нее указывает глобальный или статический указатель. Что вы хотите сделать, так это запустить valgrind с --show-reachable=yes, чтобы увидеть, является ли это проблемой.

Часто это безвредно и происходит от такой функции:

void foo()
{
    static char *buffer = 0;
    if (buffer == 0)
    {
        buffer = (char *)malloc(...);
    }
}

Этот мальлок все еще будет доступен. Но независимо от того, сколько раз вызывается foo, вы выделяете буфер ровно один раз, поэтому здесь нет никакого вреда, если вы его не освободите.

Но рассмотрим функцию, подобную этой:

void foo()
{
    static node_t *head = 0;

    node_t *node = (node_t *)malloc(sizeof(node_t));
    if (node)
    {
        node->next = head;
        head = node;
    }
    ...
}

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

Один из способов определить разницу - это посмотреть, всегда ли разные прогоны пропускают одну и ту же память или вы теряете больше памяти - это тестовые прогоны с большими входами.

Но опять же, если вы хотите быть в безопасности, используйте --show-reachable=yes и посмотрите, что происходит.

2 голосов
/ 27 января 2010

Они не просочились и не о чем беспокоиться. Память, вероятно, была выделена библиотекой C. Если вы действительно хотите знать, где они были выделены, наберите --leak-check=full --show-reachable=yes.

1 голос
/ 27 января 2010

Было бы неплохо обнулить указатели, которые были освобождены (), что привело бы к сбою при (неправильной) попытке разыменования их снова.

1 голос
/ 27 января 2010

Это дает вам адрес блока? иногда вы можете многому научиться, посмотрев, какие данные находятся в этих 568 байтах.

Хм, 568 байт, это примерно размер строки юникода MAX_PATH.

1 голос
/ 27 января 2010

Если вы уверены, что «освободили всю память, выделенную malloc», то нет, в этом нет ничего плохого. Вы не несете прямой ответственности за утечки памяти в компонентах сторонних производителей, даже если вам часто приходится обходить их.

Отчеты от Valgrind на самом деле не дают достаточно информации, чтобы мы могли вам помочь.

Я видел, как инструменты проверки памяти много раз сталкивались с ложными срабатываниями, но у меня нет прямого опыта с самим valgrind.

0 голосов
/ 30 августа 2013

Лично я всегда забываю и проверяю, как valgrind make test, который всегда добавляет хотя бы пару дополнительных по-прежнему доступных байтов ... Убедитесь, что ваше приложение запускается напрямую с помощью valgrind ... :)

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...