Sign in Join

Live chat for Free Pascal, Lazarus, Delphi and every Pascal programmer.

Mailing lists / lazarus / 2014-04

Memory leak hunt request

12 messages · 6 people · –

Reply by email Subscribe to this list Your subscription

Read-only archive. Use j and k to move between messages.

Reinier Olislagers

Hi list,

I'm often a bit dumb when it comes to memory management/memory leaks - probably because of my managed code experience (yes, excuses, excuses)...

Recently, I've looked at and helped improve TurboBird, a Firebird management tool, and I kindly got commit rights for that repository.

https://github.com/motaz/turbobird

There are still quite some leaks present, and I'd appreciate comments on what exactly to fix to get rid of them...

Thanks a lot,
Reinier

Reply by email

Graeme Geldenhuys
to Reinier Olislagers
Reinier Olislagers wrote
I'm often a bit dumb when it comes to memory management/memory leaks - probably because of my managed code experience (yes, excuses, excuses)... From my experience, develop your software from the ground up with

Heaptrc unit enabled (compiler option -gh). It is MUCH easier to fix a memory leak the second you created it, compared to 6 months down the line.

As for your question about how to resolve them. Simply enable -gh, run your app from a console window. Start simple. eg: Run the app, then immediately exit. Do memory leaks occur? If so, analyse the heaptrc output. Trace the line numbers and call stack. Go through the affected code with a fine tooth comb. Fix and repeat the test. Did the leak count reduce.

Once all "application startup" leaks have been fixed, move to another dialog, and repeat the whole process. Yes, it's painful and boring as hell. Hence my suggestion on starting development with -gh enabled and it makes it much easier.

Regards,
- Graeme -

fpGUI Toolkit - a cross-platform GUI toolkit using Free Pascal http://fpgui.sourceforge.net/

Reply by email

Reinier Olislagers
to Graeme Geldenhuys
Graeme Geldenhuys wrote
On 2014-04-26 10:31, Reinier Olislagers wrote: >From my experience, develop your software from the ground up with Heaptrc unit enabled (compiler option -gh). It is MUCH easier to fix a memory leak the second you created it, compared to 6 months down the line.

Yes. I know. Did you read my post ;) ?

Show quoted text 6 lines
As for your question about how to resolve them. Simply enable -gh, run your app from a console window. Start simple. eg: Run the app, then immediately exit. Do memory leaks occur? If so, analyse the heaptrc output. Trace the line numbers and call stack. Go through the affected code with a fine tooth comb. Fix and repeat the test. Did the leak count reduce.

Yes, I ran leakview. Apparently it wasn't clear I'm asking for help diagnosing and fixing the remaining leaks....

Reply by email

waldo kitty
to Graeme Geldenhuys: Heaptrc unit enabled (compiler option -gh). It is MUCH easier to fix a memory leak the…
Graeme Geldenhuys wrote 7 lines
On 2014-04-26 10:31, Reinier Olislagers wrote: > I'm often a bit dumb when it comes to memory management/memory leaks - > probably because of my managed code experience (yes, excuses, excuses)... From my experience, develop your software from the ground up with Heaptrc unit enabled (compiler option -gh). It is MUCH easier to fix a memory leak the second you created it, compared to 6 months down the line.

+1~~~~~ can't emphasize this enough... too many times things are developed without stack, heap and/or pointer tracking which comes back to haunt later when they are disabled for release compilations...

Show quoted text 11 lines
As for your question about how to resolve them. Simply enable -gh, run your app from a console window. Start simple. eg: Run the app, then immediately exit. Do memory leaks occur? If so, analyse the heaptrc output. Trace the line numbers and call stack. Go through the affected code with a fine tooth comb. Fix and repeat the test. Did the leak count reduce. Once all "application startup" leaks have been fixed, move to another dialog, and repeat the whole process. Yes, it's painful and boring as hell. Hence my suggestion on starting development with -gh enabled and it makes it much easier.

you've got this nailed ;)

NOTE: No off-list assistance is given without prior approval. Please keep mailing list traffic on the list unless private contact is specifically requested and granted.

Reply by email

taazz
to Reinier Olislagers: I'm often a bit dumb when it comes to memory management/memory leaks - probably because…
Reinier Olislagers wrote
There are still quite some leaks present, and I'd appreciate comments on what exactly to fix to get rid of them...

1) any steps to reproduce the leaks?
I did run the application with trace enabled and upon exit no memory leaks where reported, after that I played with it a bit creating a couple of table views and stored procedures but I didn't get any leaks reported other.
When I say I got no reports I mean that the leak file (opened it from the leakview utility) was empty.

2) Auto created forms?
Are all those needed to be create on startup? From a quick look I got the impression that they could be encapsulated in to ready made routines after a bit of clean up. It has a few questionable design(?) decisions for example it has a function in the main form
called SaveRegistrations that looks like

procedure TfmMain.FormClose(Sender: TObject; var CloseAction: TCloseAction);
begin
   if Length(RegisteredDatabases) > 0 then
     fmReg.SaveRegistrations;
   SaveAndCloseSQLHistory;
end;

and in the fmReg the saveRegistrations looks like

function TfmReg.SaveRegistrations: Boolean;
var
   F: file of TRegisteredDatabase;
   FileName: string;
   i: Integer;
begin
   try
     Sort;
     FileName:= fmMain.getConfigurationDirectory + 'turbobird.reg';
     AssignFile(F, FileName);
     FileMode:= 2;
     Rewrite(F);
     for i:= 0 to High(fmMain.RegisteredDatabases) do
       Write(F, fmMain.RegisteredDatabases[i].OrigRegRec);
     CloseFile(F);
     Result:= True;
   except
     on e: exception do
     begin
       Result:= False;
     end;
   end;
end;

and I have to ask, why it is declared in this form when everything that needs access to is on the main form?

If those 2 things I looked at are any indication of the code quality then I think that you have to spend the next 3 or 4 days cleaning up first before delving in to leak hunting.

Reply by email

Reinier Olislagers
to taazz
taazz wrote 11 lines
On 4/26/2014 12:31 PM, Reinier Olislagers wrote: > There are still quite some leaks present, and I'd appreciate comments on > what exactly to fix to get rid of them... 1) any steps to reproduce the leaks? I did run the application with trace enabled and upon exit no memory leaks where reported, after that I played with it a bit creating a couple of table views and stored procedures but I didn't get any leaks reported other. When I say I got no reports I mean that the leak file (opened it from the leakview utility) was empty.

Sorry if I didn't mention that: right-click on a table, select view first 1000 rows gives the leak.
I'm interested in finding out how to solve this one and hopefully I can learn from it.
(Fairly GUI/Laz newb here - no Delphi background).

An additional issue on Windows seems to be views/right click on a view, Display View DDL gives error message Failed to create win32 control, error 0: the operation completed succesfully...
MSDN indicates this can happen if a CreateWindowEx procedure failed; searching forum gave a hint about message hooks being used (which I suspect does not occur here); mailing list gave a suggestion that memory was corrupted leading to this problem.

Show quoted text 6 lines
2) Auto created forms? Are all those needed to be create on startup? From a quick look I got the impression that they could be encapsulated in to ready made routines after a bit of clean up. It has a few questionable design(?) decisions for example it has a function in the main form called SaveRegistrations that looks like

<snip>
Yes, agreed, there is quite some intermingling of passing data like this in the code I found.
I've been spending quite some time on getting the backend data structures improved (e.g. table, stored proc, view generation for scripts). Currently a lot of information gets transferred in the form of an sql query object which is shared between a form/module.

Thanks for the registration stuff remark, I'll include that in my consoldation effort.

Reply by email

taazz
to Reinier Olislagers
Reinier Olislagers wrote 16 lines
On 03/05/2014 14:29, taazz wrote: > On 4/26/2014 12:31 PM, Reinier Olislagers wrote: >> There are still quite some leaks present, and I'd appreciate comments on >> what exactly to fix to get rid of them... > 1) any steps to reproduce the leaks? > I did run the application with trace enabled and upon exit no memory > leaks where reported, after that I played with it a bit creating a > couple of table views and stored procedures but I didn't get any leaks > reported other. > When I say I got no reports I mean that the leak file (opened it from > the leakview utility) was empty. Sorry if I didn't mention that: right-click on a table, select view first 1000 rows gives the leak. I'm interested in finding out how to solve this one and hopefully I can learn from it. (Fairly GUI/Laz newb here - no Delphi background).

Find attached a visual aid for correcting the leak. I was expecting some harder to tell you the truth.

Show quoted text 7 lines
An additional issue on Windows seems to be views/right click on a view, Display View DDL gives error message Failed to create win32 control, error 0: the operation completed succesfully... MSDN indicates this can happen if a CreateWindowEx procedure failed; searching forum gave a hint about message hooks being used (which I suspect does not occur here); mailing list gave a suggestion that memory was corrupted leading to this problem.

from a quick look around I can't see any problems and it is in a part of the lcl that I never payed any attention so this will take longer, and I need to put it in my todo. I'll try to push it up the list but I can't promise anything at this time.

<snip>

-------------- next part --------------
A non-text attachment was scrubbed...
Name: leak.png
Type: image/png
Size: 82125 bytes
Desc: not available
URL: <http://lists.lazarus.freepascal.org/pipermail/lazarus/attachments/20140504/8fe6ee29/attachment-0001.png>

Reply by email

Reinier Olislagers
to taazz
taazz wrote 5 lines
On 5/3/2014 3:47 PM, Reinier Olislagers wrote: > On 03/05/2014 14:29, taazz wrote: >> On 4/26/2014 12:31 PM, Reinier Olislagers wrote: Find attached a visual aid for correcting the leak. I was expecting some harder to tell you the truth.

Is that the only one you found? Yes, that one is clear and simple enough. Hmmmm, yes, I was expecting something harder as well - something to do with creating visual controls and not cleaning up ;) Thanks for the research!

I suppose what I am a bit baffled by is that you can see the property access via fList.Text but the call stack does not show you the actual call (fList:=TStringList.Create) that creates the memleak...

Fixed in commit 812cff404faf35b86473eb317b3beb9fc359bf2c

Show quoted text 11 lines
> An additional issue on Windows seems to be views/right click on a view, > Display View DDL gives error message Failed to create win32 control, > error 0: the operation completed succesfully... > MSDN indicates this can happen if a CreateWindowEx procedure failed; > searching forum gave a hint about message hooks being used (which I > suspect does not occur here); mailing list gave a suggestion that memory > was corrupted leading to this problem. from a quick look around I can't see any problems and it is in a part of the lcl that I never payed any attention so this will take longer, and I need to put it in my todo. I'll try to push it up the list but I can't promise anything at this time.

No problem - glad to at least know my quick look conclusion corresponds with yours ;) As always, thanks for any help.

BTW: regardless of its problems, TurboBird can now script an entire database of mine that FlameRobin refuses to output correctly (it does not take view dependencies into account).
Currently working on getting the resulting script to run correctly and generate an identical database. Rinse and repeat, then on to more GUI issues...

As usual, hints and tips welcome!

Reply by email

zeljko
to Reinier Olislagers: Is that the only one you found? Yes, that one is clear and simple enough. Hmmmm, yes, I…
Reinier Olislagers wrote 16 lines
On 03/05/2014 23:23, taazz wrote: > On 5/3/2014 3:47 PM, Reinier Olislagers wrote: >> On 03/05/2014 14:29, taazz wrote: >>> On 4/26/2014 12:31 PM, Reinier Olislagers wrote: > Find attached a visual aid for correcting the leak. I was expecting some > harder to tell you the truth. Is that the only one you found? Yes, that one is clear and simple enough. Hmmmm, yes, I was expecting something harder as well - something to do with creating visual controls and not cleaning up ;) Thanks for the research! I suppose what I am a bit baffled by is that you can see the property access via fList.Text but the call stack does not show you the actual call (fList:=TStringList.Create) that creates the memleak... Fixed in commit 812cff404faf35b86473eb317b3beb9fc359bf2c

Would be nice to see svn revision number, instead of that hex sausage :)

zeljko

Show quoted text 31 lines
>> An additional issue on Windows seems to be views/right click on a view, >> Display View DDL gives error message Failed to create win32 control, >> error 0: the operation completed succesfully... >> MSDN indicates this can happen if a CreateWindowEx procedure failed; >> searching forum gave a hint about message hooks being used (which I >> suspect does not occur here); mailing list gave a suggestion that memory >> was corrupted leading to this problem. > from a quick look around I can't see any problems and it is in a part of > the lcl that I never payed any attention so this will take longer, and I > need to put it in my todo. I'll try to push it up the list but I can't > promise anything at this time. No problem - glad to at least know my quick look conclusion corresponds with yours ;) As always, thanks for any help. BTW: regardless of its problems, TurboBird can now script an entire database of mine that FlameRobin refuses to output correctly (it does not take view dependencies into account). Currently working on getting the resulting script to run correctly and generate an identical database. Rinse and repeat, then on to more GUI issues... As usual, hints and tips welcome! -- _______________________________________________ Lazarus mailing list http://lists.lazarus.freepascal.org/mailman/listinfo/lazarus

Reply by email

Reinier Olislagers
to Luca Olivetti: El 04/05/14 14:42, Reinier Olislagers ha escrit: Maybe because of this?…
Luca Olivetti wrote 7 lines
El 04/05/14 14:42, Reinier Olislagers ha escrit: > I suppose what I am a bit baffled by is that you can see the property > access via fList.Text but the call stack does not show you the actual > call (fList:=TStringList.Create) that creates the memleak... Maybe because of this? http://bugs.freepascal.org/view.php?id=12528

Thanks Luca,

Yes, perhaps. IIRC, though, I also ran heaptrc under FPC trunk compiled with -O-1... so that shouldn't be it...

Reply by email

Reinier Olislagers
to zeljko: Would be nice to see svn revision number, instead of that hex sausage :) zeljko
zeljko wrote 19 lines
On 05/04/2014 02:42 PM, Reinier Olislagers wrote: > On 03/05/2014 23:23, taazz wrote: >> On 5/3/2014 3:47 PM, Reinier Olislagers wrote: >>> On 03/05/2014 14:29, taazz wrote: >>>> On 4/26/2014 12:31 PM, Reinier Olislagers wrote: >> Find attached a visual aid for correcting the leak. I was expecting some >> harder to tell you the truth. > Is that the only one you found? Yes, that one is clear and simple > enough. Hmmmm, yes, I was expecting something harder as well - something > to do with creating visual controls and not cleaning up ;) > Thanks for the research! > > I suppose what I am a bit baffled by is that you can see the property > access via fList.Text but the call stack does not show you the actual > call (fList:=TStringList.Create) that creates the memleak... > > Fixed in commit 812cff404faf35b86473eb317b3beb9fc359bf2c Would be nice to see svn revision number, instead of that hex sausage :)

Don't blame me, blame git ;)

Reply by email