Delphi-PRAXiS

Delphi-PRAXiS (https://www.delphipraxis.net/forum.php)
-   Programmieren allgemein (https://www.delphipraxis.net/40-programmieren-allgemein/)
-   -   Delphi Erfahrungen bzw. Erklärungen zu AQTime gesucht (https://www.delphipraxis.net/155417-erfahrungen-bzw-erklaerungen-zu-aqtime-gesucht.html)

AJ_Oldendorf 22. Okt 2010 09:47


Erfahrungen bzw. Erklärungen zu AQTime gesucht
 
Liste der Anhänge anzeigen (Anzahl: 2)
Hallo Leute,
hat von euch schonmal jemand mit AQTime und dem Allocation Profiler gearbeitet?

Ich habe gerade mal ein kleines Testprogramm geschrieben nur um ein paar Sachen zu analysieren. Bitte nicht über den Sinn und Verstand des Quelltextes äußern, dies ist hier nicht das Thema...

Wenn ich die Anwendung mit AQTime starte und ein wenig laufen lasse (Timer Interval auf 500ms gesetzt), kann man in AQTime sagen, "GetResults Now" und man bekommt eine Auflistung über den aktuellen Speicherverbrauch.

In den Screenshots ist zu sehen, dass ich kurz nach dem Start "GetResults Now" gesagt habe (AQTime1.png) und dann nach längeren laufen lassen nochmal die Results sehen wollte (AQTime2.png).

Meine Frage ist jetzt, unter der Spalte "Size" steht immer der gleiche Wert (28 und 16). Die Adresse ändert sich aber immer und hinter dem ObjectName die Zahl wird auch größer umso länger die Anwendung läuft.

Bedeutet das jetzt, dass der Speicher durch diese zyklischen Typkonvertierungen ansteigt oder kann mir einer die Zahl nach dem ObjectName (Beispiel: vcl native memory.14752) erklären?

Ich hoffe ihr könnt mir hier bisschen helfen.
Danke schonmal und viele Grüße
AJ

Delphi-Quellcode:
unit Unit2;

interface

uses
  Windows, Messages, SysUtils, Variants, Classes, Graphics, Controls, Forms,
  Dialogs, StdCtrls, ExtCtrls;

type
  TForm2 = class(TForm)
    Button1: TButton;
    Timer1: TTimer;
    procedure Timer1Timer(Sender: TObject);
  private
    { Private-Deklarationen }
    tmpStr1 : String[10];
    tmpStr2 : AnsiString;
  public
    { Public-Deklarationen }
  end;

var
  Form2: TForm2;

implementation

{$R *.dfm}

function GetMeStr3(aStr : AnsiString) : AnsiString;
begin
  Result := '789';
end;

procedure TForm2.Timer1Timer(Sender: TObject);
begin
  tmpStr1 := '123';
  tmpStr2 := '456';

  Button1.Hint := tmpStr1 + tmpStr2;
  Button1.Hint := Button1.Hint + GetMeStr3('789');
  Button1.Hint := Copy(Button1.Hint, 1, Length(Button1.Hint) -2);
end;

end.
PS: Die Meldung Implizierte String-Umwandlung von 'AnsiString' zu 'String' hatte ich in den Optionen abgeschalten, ich weiß das diese zwei mal auftaucht

Ups... Jetzt mit Screenshot :-)

fkerber 22. Okt 2010 09:50

AW: Erfahrungen bzw. Erklärungen zu AQTime gesucht
 
Hi

Zitat:

In den Screenshots ist zu sehen
Wo? :stupid:


LG, Frederic

AJ_Oldendorf 26. Okt 2010 15:22

AW: Erfahrungen bzw. Erklärungen zu AQTime gesucht
 
push :-)
Hat das Programm bzw. den Allocation Profiler noch keiner benutzt?

Viele Grüße
AJ

Assarbad 4. Nov 2010 02:42

AW: Erfahrungen bzw. Erklärungen zu AQTime gesucht
 
Zitat:

Zitat von AJ_Oldendorf (Beitrag 1057886)
Hat das Programm bzw. den Allocation Profiler noch keiner benutzt?

Noch nicht mit Delphi/BCB. Aber in MSVC benutze ich es öfter (meist übrigens direkt aus Visual Studio heraus, dank Plugins).

Was wichtig ist sind nicht die Einzelwerte, zumindest solange du beim Gesamtwert keine Lecks findest. Dein Programm scheint periodisch was zu machen, da sich wie du schon bemerktest die Adressen ändern (der Stack, ganz unten zeigt es ja auch deutlich: TForm2::Timer1Timer). Grob gesagt sieht es für mich aus wie einmal ein AnsiString und einmal ein UnicodeString mit dem irgendwas passiert - hast ja glücklicherweise in den beiden Screenshots jeweils ein Element der anderen Größe ausgewählt. Wichtig ist kurz unter dem roten Rahmen der Wert: 2641528 für eine schnelle Gesamteinschätzung.

Allerdings ist das nur die halbe Wahrheit, bzw. die Einsteigersicht.

Nähmen wir mal an, daß es ein Leck gäbe. In diesem Fall würdest du als erstes ein Ansteigen des o.g. Wertes feststellen. Sobald du das hast, würdest du weiterhin sehen welcher Objekttyp (und jetzt ist die Einzelauflistung wichtig) da leckt. Das ist alles aber nur wichtig, solange eine periodische Aktion stattfindet. Ansonsten sollte man zuallererst das Programm laufen lassen ... irgendwas machen was man eben so im Programm macht und es dann beenden. Dann wird man sehen, ob es schonmal unter normalen Umständen Lecks gibt - wobei AQTime ja auch auf Ressourcenlecks wie GDI-Lecks prüfen kann (zumindest die Pro).

Interessanter finde ich bei AQTime allerdings (habe die Pro sowohl auf Arbeit als auch privat) "Platform Compliance" (statisch), "Performance Profiler" (geht bis zeilenweise Genauigkeit) und "Exception Trace Profiler". Um Lecks zu finden eignen sich m.E.n. besser die Funktionen die ohnehin dafür zuständig sind. Also der MM bei Delphi. Und auch die CRT bei MSVC bringt schon alles mit um sowohl Speicherlecks als auch korrumpierte Heaps aufzuspüren. Für bestimmte Dinge eignet sich auch der Profiler der das Laden von DLLs überwacht. Aber hängt vom Programm ab usw. ...

Noch genialer als alles vorgenannte finde ich allerdings Bei Google suchenValgrind. Valgrind emuliert den Prozessor zu weiten Teilen, läuft also deutlich langsamer. Allerdings wird "tainted memory" verwendet. Jede Speicheranforderung resultiert also in einem Block der von Valgrind als noch nicht initialisiert markiert wird. Dann kann das Programm damit machen was es will, inklusive weiterkopieren usw. ...
Wenn nun Code an späterer Stelle eine Entscheidung aufgrund uninitialisierten Speichers trifft (bspw. if auf ein Array-Element), wird dies mokiert. Ob Speicher als uninitialisiert gilt, wird vererbt (also beim Kopieren von Speicher)! Desweiteren werden alle möglichen Speicherverletzungen (doppelt freigeben, Stack überschreiben, Heap überschreiben, in freigegebenen oder ohnehin nicht allozierten Speicher schreiben) angezählt und zusammen mit einem Stackdump gelistet. Der Stackdump enthält auf die Zeile genau (gcc ... -ggdb -g3) was schiefging und bei Speicherverletzungen auch die Adresse der Stelle wo der Speicher ursprünglich alloziert wurde (inkl. Stack, wenn es auf dem Stack lag). Leider gibt es Valgrind nur für unixoide Systeme und es setzt DWARF-Debuginfos voraus. Aber bei plattformunabhängigem Code habe ich bisher noch nichts besseres gefunden.


Alle Zeitangaben in WEZ +1. Es ist jetzt 06:46 Uhr.

Powered by vBulletin® Copyright ©2000 - 2024, Jelsoft Enterprises Ltd.
LinkBacks Enabled by vBSEO © 2011, Crawlability, Inc.
Delphi-PRAXiS (c) 2002 - 2023 by Daniel R. Wolf, 2024 by Thomas Breitkreuz