Einzelnen Beitrag anzeigen

markusef

Registriert seit: 9. Mai 2016
15 Beiträge
 
Delphi 10 Seattle Professional
 
#3

AW: ADO Memoryleak / Speicherleck ?!

  Alt 29. Nov 2017, 13:57
Hey, Sorry ich hab mich bei der Erklärung nicht ordentlich ausgedrückt.
Also ich habe eine Klasse "tdatabaseinfo" abgeleitet von TDataModule inkl. einer Form wo die ADOConnection als Komponente drauf liegt.
Diese Klasse erzeuge ich im execute-Teil des Threads und gebe sie auch mit FreeAndNil wieder frei. Das passiert innerhalb des Threads
in einer "while not terminated"-Schleife, mit sleep dazwischen.

Quellcode:

Thread create:
Code:
constructor TWorkerThread.create(aCreateSuspended: Boolean; aConnStr : String; aHost : String; aPort : Word; aSleepTime : Integer);
begin
  inherited create(aCreateSuspended);
  FreeOnTerminate := false;
  fConnStr       := aConnStr;
  fSleepTime     := aSleepTime;
  fHost          := aHost;
  fPort          := aPort;
  fConnected     := false;

  fTcpClient               := TIdTCPClient.Create(nil);
  fTcpClient.Host          := aHost;
  fTcpClient.Port          := aPort;
  fTcpClient.ConnectTimeout := 3000;
  fTcpClient.ReadTimeout   := fSleepTime;

  MsgCenter := TMsgCenter.Create(fConnStr);
  ErrCnt   := 0;

  nxLogging.Logger.info('TWorkerThread.create', 'created..');
end;
Thread execute:
Code:
procedure TWorkerThread.execute;
var
  ServerMsg  : String;
begin
  inherited;
  try
    fTcpClient.Connect;
    fConnected := true;

    nxLogging.Logger.trace('TWorkerThread.execute', 'tcp connected');
  except
    on e: Exception do
    begin
      nxLogging.Logger.error('TWorkerThread.execute', e.Message);
    end;
  end;

  while not self.Terminated do
  begin
    try
      if fTcpClient.Connected then
      begin
        databaseInfo := TdatabaseInfo.Create(nil);
        databaseInfo.ConnectionString := fConnectionString;

        if not databaseInfo.isConnected then
        begin
          databaseInfo.Connect;
        end;

        //do stuff, auskommentiert..

        databaseInfo.Disconnect;
        FreeAndNil(databaseInfo);
      end
      else
      begin
        nxLogging.Logger.error('TWorkerThread.execute', 'tcp connection failed');
        Reconnect;
      end;
    except
      on E: Exception do
      begin
        nxLogging.Logger.error('TWorkerThread.execute', 'error: ' + e.Message);
        Reconnect;
      end;
    end;
    sleep(fSleepTime);
  end;
  fTcpClient.Disconnect;
  nxLogging.Logger.trace('TWorkerThread.execute', 'tcp disconnected');
end;
databaseInfo.Connect:
Code:
function TdatabaseInfo.Connect : boolean;
begin
  try
    if fConnectionString <> '' then
    begin
      ADOConnection.ConnectionString := fConnectionString; // Übergibt Connection String
    end
    else
    begin
      Result := false;
      nxLogging.Logger.error('TdatabaseInfo.Connect', 'connection string empty');
      Exit;
    end;

    ADOConnection.Open;

    if ADOConnection.Connected then
    begin
      Result := true;
    end;
  except
    on e : exception do
    begin
      Result := false;
      nxLogging.Logger.error('TdatabaseInfo.Connect', 'error during ADO connect: ' + E.Message);
    end;
  end;
end;
databaseinfo.Disconnect:
Code:
function TdatabaseInfo.Disconnect : boolean;
begin
  try
    ADOConnection.Close;
    ADOConnection.Connected := false;
  finally
    Result := true;
  end;
end;

Jedesmal wenn der Thread durch die while-Schleife rennt steigt der Arbeitsspeicher um ein paar hundert Kilobyte.
Markus
  Mit Zitat antworten Zitat