Delphi/FPC: утекает память в IntToHex
а fastmm из 2k7 что говорит?
сорри, я 2007 в глаза не видел ни разу, поставил триал чтобы проверить эти лики.
названия обнадёживающие. как этим FastMM пользоваться?
названия обнадёживающие. как этим FastMM пользоваться?
fastmm - сторонний менеджер памяти, который был в D2006 сделан по умолчанию заместо предыдущего (который в D7). менеджер умеет ловить leaks, так что если ты включишь какую-то там опцию (fulldebugmode и еще что-то то прога каждый раз при завершении будет плеваться о том, сколько памяти утекло, уточняя какие переменные именно и какие процедуры "глюканули" (последняя версия sourceforge.net/projects/fastmm/, на D7 работает). качни, поставь и проверь. если не будет плеваться, значит все ок
кроме того, у этого fastmm есть такой прикол, что он может память явно (т.е. через virtualfree) не освобождать сразу после вызова деструктора \ freemem-а. а может как-то ее по-хитрому кэшировать. у меня была такая ситуация: в многопоточном приложении в подгружаемой DLL выделялось в нескольких потоках по двумерному массиву по 400 мегабайт каждый (потом с массивами была работа НО при освобождении массивов прога память не освобождала и диспетчер памяти показывал, что прога выделила сотни мегабайт.
з.ы. переходи на D2007
кроме того, у этого fastmm есть такой прикол, что он может память явно (т.е. через virtualfree) не освобождать сразу после вызова деструктора \ freemem-а. а может как-то ее по-хитрому кэшировать. у меня была такая ситуация: в многопоточном приложении в подгружаемой DLL выделялось в нескольких потоках по двумерному массиву по 400 мегабайт каждый (потом с массивами была работа НО при освобождении массивов прога память не освобождала и диспетчер памяти показывал, что прога выделила сотни мегабайт.
з.ы. переходи на D2007
Оборачиваете все в цикл и повторяете 100-10000 раз. У меня количество памяти при этом не возрастает - а значит утечки нет. Если вас интересует почему разница не в 400 байт - так не забывайте про структуры кучи, выравнивание в ней, резерв массива и.т.д.
тут ты не прав.
сделай не циклом, а линейный участок на 100 таких действий. тебя кое-что удивит
сделай не циклом, а линейный участок на 100 таких действий. тебя кое-что удивит

в общем, шаманство с массивами можно выкинуть.
делаем так:
Если брать FastMM, то FastGetHEapStatus тоже показывает увеличение TotalAllocated на каждый вызов IntToHex на 20байт.
Цикл такого эффекта не даёт. независимо от длины цикла утекает ровно 20 байт.
если в цикле два раза IntToHex, то утечёт 40.
однако после завершения работы Fast отчёта не даёт.
делаем так:
WriteLn(IntToHex(Integer(Pointer(a8;
WriteLn(IntToHex(Integer(Pointer(a8;
WriteLn(IntToHex(Integer(Pointer(a8;
WriteLn(IntToHex(Integer(Pointer(a8;
WriteLn(IntToHex(Integer(Pointer(a8;
WriteLn(IntToHex(Integer(Pointer(a8;
WriteLn(IntToHex(Integer(Pointer(a8;
WriteLn(IntToHex(Integer(Pointer(a8;
WriteLn(IntToHex(Integer(Pointer(a8;
WriteLn(IntToHex(Integer(Pointer(a8;
WriteLn(IntToHex(Integer(Pointer(a8;
WriteLn(IntToHex(Integer(Pointer(a8;
WriteLn(IntToHex(Integer(Pointer(a8;
WriteLn(IntToHex(Integer(Pointer(a8;
WriteLn(IntToHex(Integer(Pointer(a8;
WriteLn(IntToHex(Integer(Pointer(a8;
WriteLn(IntToHex(Integer(Pointer(a8;
WriteLn(IntToHex(Integer(Pointer(a8;
WriteLn(IntToHex(Integer(Pointer(a8;
WriteLn(IntToHex(Integer(Pointer(a8;
WriteLn(IntToHex(Integer(Pointer(a8;
WriteLn(IntToHex(Integer(Pointer(a8;
WriteLn(IntToHex(Integer(Pointer(a8;
Если брать FastMM, то FastGetHEapStatus тоже показывает увеличение TotalAllocated на каждый вызов IntToHex на 20байт.
Цикл такого эффекта не даёт. независимо от длины цикла утекает ровно 20 байт.
если в цикле два раза IntToHex, то утечёт 40.
однако после завершения работы Fast отчёта не даёт.
Сделал - независимо от числа inttohex'ов разница в 32 байта. Впрочем, даже если бы она росла, это не было бы утечкой - мало ли какие паскаль временные переменные создает. Вот если память растет в цикле - это утечка. Так что пока у вас нет такого примера - не надо будоражить общественность.
Я уже не говорю о том, что исходники IntToHex можно и посмотреть. В FPC 2.2.0 и 2.2.1 она выглядит так:
Я уже не говорю о том, что исходники IntToHex можно и посмотреть. В FPC 2.2.0 и 2.2.1 она выглядит так:
{ IntToHex returns a string representing the hexadecimal value of Value }
const
Heigits: array[0..15] of char = '0123456789ABCDEF';
function IntToHex(Value: integer; Digits: integer): string;
var i: integer;
begin
SetLength(result, digits);
for i := 0 to digits - 1 do
begin
result[digits - i] := Heigits[value and 15];
value := value shr 4;
end ;
while value <> 0 do begin
result := Heigits[value and 15] + result;
value := value shr 4;
end;
end ;Я уже не говорю о том, что исходники IntToHex можно и посмотреть.В D7 она реализована на асме.
Кстати, интересно вот что: под D6 такой-же эффект тоже сохранялся?
А асм надо знать!
ага,
вот это что означает?
такая инструкция предшествует непосредственно запихиванию аргументов в регистры и вызову IntToHex
lea eсx, [ebp-$04]
вот это что означает?
такая инструкция предшествует непосредственно запихиванию аргументов в регистры и вызову IntToHex
> вот это что означает?
ecx=ebp-4 всего лишь
ecx=ebp-4 всего лишь
ecx=ebp-4 всего лишьпо-моему, скобочки [ebp-4] означают взятие содержимого по адресу ebp-4
а lea по-твоему что означает?
А lea - взятие адреса.
ecx = &*(ebp-4)
ecx = &*(ebp-4)
Сборка с debug DCUs и выполнение с установкой брейкпоинтов на SysGetMem, SysFreeMem и SysReallocMem показала что в inttohex выделяется память под строку, которая после выполнения writeln не освобождается. Тоже самое, в общем-то, происходит и с inttostr, кстати. Но эти строки освобождаются перед выходом из текущей функции/процедуры, для подтверждения этого достаточно выделить большую часть приведённого кода в отдельную функцию и проверить перед её вызовом и после количество выделенной памяти.
Короче, нечего бить тревогу: никаких утечек здесь нет и быть не может.
ps: у меня D7, если что..
pps: и чем это я на работе занимаюсь?
Короче, нечего бить тревогу: никаких утечек здесь нет и быть не может.
ps: у меня D7, если что..
pps: и чем это я на работе занимаюсь?
если fastmm не ругается (при учете включенной проверки на leakи значит все в порядке.
Добро пожаловать в мир подсчёта ссылок, Вася
Ну я-то и так все на java пишу, используя паскаль и асм только для задач (в основном переборных где нужна максимальная производительность.
Оставить комментарий
yolki
проверено на D7/D2007 (утекает 20 байт на вызов)проверено в FPC 2.2.0 (утекает 16 байт на вызов)
Кто-нибудь может что-то прокомментировать?