Page 1 of 2

Memory leak? or am I doing something wrong?

Posted: 06.12.2005, 12:32
by Pengwin
I am having a problem with the ZeosLib (6.1.5) linking with Firebird 1.5.2 in my Delphi 4 (yes, I am really using Delphi 4) app. Whenever I send an SQL command using the TZQuery object, my apps memory usage seems to increase. However, it never seems to decrease. I first noticed this on an app I am writing for my employer, it rose from 7MB memory usage to 120MB in about 30 minutes.
To confirm that it wasn't my program I wrote a small test which also seems to exhibit the same behaviour. Whilst this code is minimal, it essentially does the same thing. Could someone please let me know if I am missing something?
The program simply has a timer, button, edit box, TZConnection and TZQuery on it.

Code: Select all

unit Unit1;

interface

uses
  Windows, Messages, SysUtils, Classes, Graphics, Controls, Forms, Dialogs,
  StdCtrls, Db, ZAbstractRODataset, ZAbstractDataset, ZDataset, ZConnection,
  ExtCtrls;

type
  TForm1 = class(TForm)
    ZConnection1: TZConnection;
    ZQuery1: TZQuery;
    Button1: TButton;
    Edit1: TEdit;
    Timer1: TTimer;
    procedure Button1Click(Sender: TObject);
    procedure Timer1Timer(Sender: TObject);
  private
  public
  end;

var
  Form1   : TForm1;

implementation

{$R *.DFM}

procedure TForm1.Button1Click(Sender: TObject);
begin
  timer1.enabled := not timer1.enabled;
  edit1.readonly := timer1.enabled;
end;

procedure TForm1.Timer1Timer(Sender: TObject);
begin
  try
    try
      if not ZConnection1.Connected then
        ZConnection1.Connect;
      ZQuery1.SQL.text := edit1.text;
      ZQuery1.Open;
      ZQuery1.first;
      if ZQuery1.Eof then
        caption := 'empty'
      else
        caption := 'records';
    except
      on e: exception do
        caption := e.message;
    end
  finally
    ZQuery1.close;
  end;
end;

end.

Posted: 06.12.2005, 13:03
by Pengwin
As a test, I connected the same program (above) to a MySQL database. I get the same symptoms with a rapidly escalating memory usage.

Posted: 07.12.2005, 01:03
by zippo
Hmmm... never had those problems. I upgraded to 6.1.5 recently, but it seems sto work OK.. If I discover something I'll post it here.

Posted: 07.12.2005, 11:30
by laurentlaffont
ZeosLib has a lot of memory leaks when openning/closing datasets. Compile it with FastMM (memory leak reporting - http://sourceforge.net/projects/fastmm/) and may be you debug it.

Posted: 07.12.2005, 21:57
by zippo
True, but I saw only small leaks - here we are takling about 120 MB in 30 minutes - my leaks are max 1-2 Mb in few days/weeks!

Posted: 07.12.2005, 23:19
by btrewern
I've just tried your app using Delphi 7 with ZeosLib 6.1.5 (and all the patches) and using FastMM4, and haven't found any problems.

Have you applied the patches on the Sourceforge site? I think you may have a problem with your installation. I did use Zeos 6.1.5 with Delphi 4 and didn't have any problems.

Ben

Posted: 07.12.2005, 23:37
by btrewern
Does the following fix the problem?

Code: Select all

procedure TForm1.Timer1Timer(Sender: TObject); 
begin
  [b]Timer1.Enabled := False;[/b]
  try 
    try 
      if not ZConnection1.Connected then 
        ZConnection1.Connect; 
      ZQuery1.SQL.text := edit1.text; 
      ZQuery1.Open; 
      ZQuery1.first; 
      if ZQuery1.Eof then 
        caption := 'empty' 
      else 
        caption := 'records'; 
    except 
      on e: exception do 
        caption := e.message; 
    end 
  finally 
    ZQuery1.close; 
  end; 
  [b]Timer1.Enabled := True;[/b]
end;
Ben

Posted: 08.12.2005, 11:06
by Pengwin
zippo :
True, but I saw only small leaks - here we are takling about 120 MB in 30 minutes - my leaks are max 1-2 Mb in few days/weeks!
The main app I am develooping is performing a LOT of data access (at least 10 requests a second, potentially much more). Therefore, these little leaks mount up to a huge problem.


btrewern :
Have you applied the patches on the Sourceforge site
I have applied all the patches available

btrewern : The code you suggested may work with the test program, but my main app is a multi-threaded data server that doesn't use a TTimer object.

I am going to see if I get the same error with the latest Alpha release, however I did check my code by using another component for the firebird access and the memory of the test program stabilised after two or three reads. I would prefer to use Zeos though as it offers the chance to create a data server that can access different types of database.

Posted: 09.12.2005, 10:57
by zippo
Pengwin, my app does a lot of queries, too. I must admit I'm not an expert for leak searching (I just watch the task manager.. :) ), so is there any tutorial and/or tools for this?

Posted: 09.12.2005, 11:43
by Pengwin
zippo : I first noticed the leak by watching the task manager. This led me to create the test app I posted here, which also exhibited the same behaviour. To confirm it wasn't FB itself, I changed the access to a MySQL db. This gave the same behaviour. So then I replaced the Zeos components with another FB data access component suite (not as comprehensive as Zeos) and this eradicated the problem. Finally, I used FastMM to show me the problems, and this gave me an 8000+ line report of the problem areas, all of which seemed to be in the Zeos units. Unfortunately, I do not have the time to hunt down and fix each of the problems specified in the report. Therefore I have abandoned Zeos for this project :( , which is a real shame because I do like the way they give me the ability to access most of the database types I potentially need access to.
I attempted to install the alpha of the latest release, but Zeos no longer supports Delphi 4, so that was also abandoned.

Posted: 11.12.2005, 18:14
by btrewern
Were you using one ZConnection component between more than one thread? I don't think that would be safe.

I've used zeos within a threaded application now for some time but always used a seperate ZConnection for each thread. Or you could use a single, or pool of connections and seralize the database access. (See http://www.arcanatech.com and TDataModulePool).

PS I'm sorry to hear you have abandoned Zeos

Posted: 12.12.2005, 19:46
by Pengwin
Were you using one ZConnection component between more than one thread? I don't think that would be safe.

I've used zeos within a threaded application now for some time but always used a seperate ZConnection for each thread. Or you could use a single, or pool of connections and seralize the database access. (See http://www.arcanatech.com and TDataModulePool).

PS I'm sorry to hear you have abandoned Zeos
Yes, I was using a seperate ZConnection in each thread. But as you can also see, this was not necessary in the test app that I posted.

I have not completely abandoned Zeos. I like the components a great deal, however, it is too late for this project.

If I can resolve this issue I have, I will be using them in the furture for other applications.

Thanks for the link to the pooling components, I will look at them, although I notice from the website that they are for Delphi 5-7, so I may have to rework them slightly to get them to work with Delphi 4.

Posted: 13.12.2005, 07:43
by klchin
Hi Pengwin,

Is there any different if you runtime create the
both TZConnect and TZQuery?

Regards
KL Chin

Posted: 13.12.2005, 09:56
by Pengwin
klchin wrote:Hi Pengwin,

Is there any different if you runtime create the
both TZConnect and TZQuery?

Regards
KL Chin
No. In my test app I used design time components. In the actual project, I created the components at runtime.

Posted: 14.12.2005, 03:16
by klchin
Hi,

Have you try explicitly free/delete the object after close?