Einzelnen Beitrag anzeigen

Christian Seehase
(Co-Admin)

Registriert seit: 29. Mai 2002
Ort: Hamburg
11.105 Beiträge
 
Delphi 11 Alexandria
 

Re: bedarf des Arbeitsspeichers meiner Anwendung verringern

  Alt 9. Mai 2007, 23:00
Moin gabneo,

Zitat von gabneo:
Daher die Frage, warum ist eine Anwendung wie Ultramon und viele weitere Anwendungen so klein(?), wenn nichts was ich meines wissens beeinflussen kann, die größe im Arbeitsspeicher verringert?
Mir stellt sich da eher die Frage, was die Werte zu bedeuten haben, die der Taskmanager dort anzeigt.
Zumindest unter XP ist die Allocation Granularity (siehe GetSystemInfo) 64Kb, dass heisst, wenn Speicher beim System angefordert wird (per VirtualAlloc), wird auf jeden Fall ein 64Kb grosser Block zugewiesen.
Den kann man dann, in Pagesize-Schritten (i.d.R. 4Kb) belegen.
Es könnte gut sein, dass der Taskmanager nur den Speicher anzeigt, der den Typ MEM_COMMIT hat, und nicht was nur MEM_RESERVED hat, auch wenn dieser Speicher dem System nicht mehr zur Verfügung steht.

Speicher kann drei Stati haben:
free, reserved, commited
free kann von jedem der es anfordert belegt/angefordert werden.
reserved sind die Speicherbereiche, die erst einmal angefordert wurden, so dass sie dem System nicht mehr zur Verteilung zur Verfügung stehen, sondern von einem Prozess reserviert wurden.
commited sind die Speicherseiten, mit denen ein Prozess arbeiten (schreiben / lesen) kann.

Mit diesem Codeschnipsel kannst Du ermitteln, wieviel Speicher für Dein Programm reserviert ist:

Delphi-Quellcode:
var
  hProc : DWORD;
  pMemStart : Pointer;
  dwRead : DWORD;
  mbi : MEMORY_BASIC_INFORMATION;
  dwTotalSize : DWORD;
  dwCommittedSize : DWORD;

begin
  hProc := OpenProcess(PROCESS_ALL_ACCESS,true,GetCurrentProcessId);
  if hProc = 0 then exit;
  try
    dwTotalSize := 0;
    dwCommittedSize := 0;
    pMemStart := nil;
    dwRead := VirtualQueryEx(hProc,pMemStart,mbi,SizeOf(mbi));
    while dwRead = SizeOf(mbi) do begin
      if mbi.State = MEM_COMMIT then begin
        Inc(dwCommittedSize,mbi.RegionSize);
        Inc(dwTotalSize,mbi.RegionSize);
      end;
      if mbi.State = MEM_RESERVE then begin
        Inc(dwTotalSize,mbi.RegionSize);
      end;
      pMemStart := Pointer(DWORD(mbi.BaseAddress)+mbi.RegionSize);
      dwRead := VirtualQueryEx(hProc,pMemStart,mbi,SizeOf(mbi));
    end;
  finally
    CloseHandle(hProc);
  end;
  ShowMessage('Committed: '+IntToStr(dwCommittedSize div 1024)+#13#10+'Total: '+IntToStr(dwTotalSize div 1024));
end;
Wenn Du statt GetCurrentProcessId die Prozess-Id eines anderen Prozesses nimmst, solltest Du die Werte des Prozesses bekommen.
Unter Vista wirst Du wahrscheinlich für die Zugriffsrechte auf einen fremden Prozess PROCESS_QUERY_INFORMATION angeben müssen

Ersatzweise könntest Du Dir auch mal den ProcessExplorer von Sysinternals (http://www.microsoft.com/technet/sys...s/default.mspx) herunterladen. Dort kannst Du Dir verschiedenste Speicherbereiche die ein Prozess belegt ansehen. Was der Taskmanager anzeigt, müsste dem Working Set entsprechen.
Ausserdem kannst Du natürlich auch noch ein bisschen weiter mit den verschiedenen Bestandteilen von MEMORY_BASIC_INFORMATION "herumspielen", um verschiedene Informationen zum Speicher zu erhalten.
Tschüss Chris
Die drei Feinde des Programmierers: Sonne, Frischluft und dieses unerträgliche Gebrüll der Vögel.
Der Klügere gibt solange nach bis er der Dumme ist
  Mit Zitat antworten Zitat