Heapoversize bei hBitmap laden in WM_CREATE



  • Hallo,

    Ich lade ein bitmap während die Callback des Fensters die msg WM_CREATE abarbeitet. Das funktioniert auch wunderbar aber der benötigte Arbeitsspeicher wächst auf 35MB zusätzlich an. Das Interessante daran ist, wenn ich das Fenster minimiere verschwinden die 35MB und bleiben nach dem wiederherstellen auf originalgröße auch verschwunden, dass bild jedoch erhalten.

    (das gleiche verhalten tritt auch auf wenn vor dem msg switch der handle

    static hbit=(HBITMAP)LoadBitmap/LoadImage(...)
    

    gleich zugewiesen wird!)

    Kann mir jemand bitte erklären? 😋

    Seid gegrüßt


  • Mod

    Und von welchen Wert sprichst Du?



  • Moin Martin,

    (ich hoffe ich verstand Deine Frage auf meine Frage richtig...)

    Zur Laufzeit benötigt dass Programm rund 3 bis 4,5MB, wobei das meiste davon wohl der stack ist.
    Erzeuge ich das Fenster (WS_CHILD) mit entsprechender CALLBACK:

    LONG_PTR CALLBACK blub(...)
    
    static HBITMAP hBit=NULL;
    
    switch(message)
    
    case WM_CREATE:
    
    hBit=(HBITMAP)LoadBitmap()
    ....
    

    Vergrössert sich der Heap um der Bildgröße entsprechende weise so das der Speichererbrauch bei rund 40MB liegt.
    Minimiere ich jetzt dass (Parent) Fenster, so verschwinden die zusätzlichen
    35MB, stelle ich es wieder her so ist der Speicherbedarf rund bei 3 bis 4,5 MB.
    Das geladene Bild wird aber noch vollständig verwendet.

    Wär natürlich cool wenn mir jemand den trick erklären könnte, dann könnte ich
    evtl. dass Bild gleich so Laden dass der Speicherverbrauch nach dem Laden
    seine größe beibehält.

    Sei gegrüßt und habe dank...


  • Mod

    Von welchem Speichert Wert sprichst Du?
    Wie erittlest Du den Speicherverbrauch?
    Working Set Size, oder was?



  • Hier einmal die Performance info und WorkingSetSize ProcessMemoryCounters ermittelt durch:

    SIZE_T  dwMin, dwMax;
    			HANDLE hProcess;
    			hProcess = OpenProcess( PROCESS_QUERY_INFORMATION, 
                                FALSE,  GetCurrentProcessId());
    if (hProcess)
    {
    
    	PPERFORMANCE_INFORMATION pi;
    	GetPerformanceInfo(pi,sizeof(PERFORMANCE_INFORMATION));
    
            PPROCESS_MEMORY_COUNTERS_EX pmc;
    	GetProcessMemoryInfo(hProcess,(PPROCESS_MEMORY_COUNTERS)pmc,sizeof(PROCESS_MEMORY_COUNTERS_EX));
    				GetProcessWorkingSetSize(hProcess, &dwMin, &dwMax);
    								CloseHandle(hProcess);
    }
    

    vor:

    (PERFORMANCEINFO)
                    cb	        56	unsigned long
    		CommitTotal	269723	unsigned long
    		CommitLimit	1005400	unsigned long
    		CommitPeak	480817	unsigned long
    		PhysicalTotal	521172	unsigned long
    		PhysicalAvailable	235454	unsigned long
    		SystemCache	205677	unsigned long
    		KernelTotal	36548	unsigned long
    		KernelPaged	25682	unsigned long
    		KernelNonpaged	10866	unsigned long
    		PageSize	4096	unsigned long
    		HandleCount	26594	unsigned long
    		ProcessCount	79	unsigned long
    		ThreadCount	835	unsigned long
    (WORKINGSETSIZE)
    		dwMin	204800	unsigned long
    		dwMax	1413120	unsigned long
    (PROCESSMEMORYCOUNTERSEX)
    		PageFaultCount	15888	unsigned long
    		PeakWorkingSetSize	42532864	unsigned long
    		[b]WorkingSetSize	42528768	unsigned long[/b]
    		QuotaPeakPagedPoolUsage	199524	unsigned long
    		QuotaPagedPoolUsage	198828	unsigned long
    		QuotaPeakNonPagedPoolUsage	5464	unsigned long
    		QuotaNonPagedPoolUsage	4840	unsigned long
    		PagefileUsage	10117120	unsigned long
    		PeakPagefileUsage	10280960	unsigned long
    		PrivateUsage	10117120	unsigned long
    

    danach:

    (PERFORMANCEINFO)
    		cb	56	unsigned long
    		CommitTotal	272586	unsigned long
    		CommitLimit	1005400	unsigned long
    		CommitPeak	480817	unsigned long
    		PhysicalTotal	521172	unsigned long
    		PhysicalAvailable	239575	unsigned long
    		SystemCache	213589	unsigned long
    		KernelTotal	36970	unsigned long
    		KernelPaged	26086	unsigned long
    		KernelNonpaged	10884	unsigned long
    		PageSize	4096	unsigned long
    		HandleCount	26508	unsigned long
    		ProcessCount	79	unsigned long
    		ThreadCount	829	unsigned long
    (WORKINGSETSIZE)
                    dwMin	204800	unsigned long
    		dwMax	1413120	unsigned long
    (PROCESSMEMORYCOUNTERSEX)
    		PageFaultCount	25809	unsigned long
    		PeakWorkingSetSize	42565632	unsigned long
    		[b]WorkingSetSize	2834432	unsigned long[/b]
    		QuotaPeakPagedPoolUsage	199524	unsigned long
    		QuotaPagedPoolUsage	198876	unsigned long
    		QuotaPeakNonPagedPoolUsage	5464	unsigned long
    		QuotaNonPagedPoolUsage	4880	unsigned long
    		PagefileUsage	10129408	unsigned long
    		PeakPagefileUsage	10280960	unsigned long
    		PrivateUsage	10129408	unsigned long
    

    Sichtbar verkleinert sich working Setsize vom Peak auf die sichtbare größe.

    Meine frage nun ist Warum?

    Dank Dir im voraus Martin 😃



  • Hi,

    noch ein paar fragen zum Thema:

    Hat jemand eine idee warum die Working set size reduziert wird?

    Wird der handle assoziierte inhalt nach dem minimieren ausgelagert?
    -Kann dieser "manuell" ausgelagert werden?
    -Wohin wird dieser ausgelagert?
    Wenn dieser nicht ausgelagert wird, wohin "verschwindet" dieser?

    Wird der content evtl erst geladen und nach dem minimieren nur noch auf das .data segment mit dem handle referenziert?
    -Wenn ja kann man das gleich/"manuell" machen?

    Wenn ein Handle assoziiertes object nicht im Heap liegen würde, wo dann?

    Kann mir jemand links und/oder erklärungen dazu geben?

    Seid gegrüßt


  • Mod

    Windows trimmed den WorkingSet Size wenn eine Anwendung minimiert ist oder manchmal auch wenn sie im Hintergrund liegt.

    Das macht der Speichermananger automatisch.
    Allerdings ist die Working Set Size kein Indikator für großen Speicherhunger.

    Seit Windows Vista geht Windows noch aggressiver mit freiem Speicher um, es überalloziert faktisch Anwendungen, weil es billiger ist Speicher später freizugeben, als Speicher bei Bedarf nachzuallokieren.

    Das wird zum Beispiel auch hier diskutiert:
    http://www.getdotnetcode.com/gdncstore/free/Articles/The Memory Mystery.htm


Anmelden zum Antworten