Archiv verlassen und diese Seite im Standarddesign anzeigen : [C] Eigenen Speicherverbrauch bestimmen
BLUESCREEN3D
23-04-2006, 22:29
Wie kann ein C-Programm zur Laufzeit seinen eigenen Speicherverbrauch bestimmen?
Ich dachte eigentlich, dass das mit getrusage() gehen würde, was es aber nicht tut...
Ich will die Informationen nicht aus /proc auslesen sondern über irgendeine C-Funktion (sowas muss es doch geben - konnte aber nichts finden :/).
RapidMax
29-04-2006, 23:15
Nun das ist nicht ganz einfach. Zur Theorie:
Dein Programm hat einen Datenbereich, der wachsen kann. wenn du mit malloc() Speicher anforderst, dann wird dieser aus dem Datenbereich angefordert. Ist der Datenbereich zu klein, vergrössert malloc() den Datenbereich über brk(). Allerdings werden grosse, angeforderte Bereiche (ca. >128kBytes) mittels mmap() angefordert.
Für debugging-Zwecke gibt es bei malloc der glibc die funktion mallinfo() (aus malloc.h). Das Problem hier ist nun, dass die grossen, mit mmap() allozierten Bereiche nicht in dieser Statistik aufgeführt sind. Wie man zu diesen kommt, weiss ich nicht. malloc_stats() gibt diese zwar aus, aber als Text auf stdout.
Hier noch ein kleines Progrämmchen zum spielen (z.B. auch mal mit strace):
#include <unistd.h>
#include <stdio.h>
#include <malloc.h>
void info() {
struct mallinfo mi = mallinfo();
printf("non-mmapped space allocated from system: %d\n"
"number of free chunks: %d\n"
"number of fastbin blocks: %d\n"
"number of mmapped regions: %d\n"
"space in mmapped regions: %d\n"
"maximum total allocated space: %d\n"
"space available in freed fastbin blocks: %d\n"
"total allocated space: %d\n"
"total free space: %d\n"
"top-most, releasable (via malloc_trim) space: %d\n",
mi.arena, mi.ordblks, mi.smblks, mi.hblks, mi.hblkhd,
mi.usmblks, mi.fsmblks, mi.uordblks, mi.fordblks,
mi.keepcost);
}
int main() {
void *allocated[100];
void *p1;
int i;
info();
for (i = 0; i < sizeof(allocated); i++) {
allocated[i] = malloc(4024);
}
info();
p1 = malloc(0x100000);
info();
malloc_stats();
return 0;
}
Ich habe bei den Recherchen folgenden Artikel gefunden, der das oben Beschriebene abdeckt: http://www.linuxjournal.com/article/6390
Gruss, Andy
KaiGillmann
04-05-2006, 07:58
Was für mich eine Lösung wäre, wäre die Funktionssammlung zur Speicherverwaltung (malloc und so) alle in neue Funktionen zu kapseln (oder ähnlich).
Als primitives Beispiel:
int UsedMemory = 0; // Speicherzähler global damit man mit allen Speicherfunktionen den erhöhen kann - static reicht net
void *MyMalloc(size_t size)
{
UsedMemory += size;
return malloc(size);
}
Das als SEHR primitives Beispiel, aus dem Kopf, ohne garantie auf Funktion :) Um zu zeigen was ich meine.
So oder so ähnlich arbeiten, meines wissens nach, Bibliotheken zum finden von Speicherleks und ähnlichem. Wie gesagt, war ausm Kopf, weiss es nicht mehr genau.
Das Problem an dieser Geschichte ist, dass du damit nur dynamisch allokiertem Speicher zählen kannst, sprich "int UsedMemory" ist da nicht mal drin. Es wird also nur Heap gezählt. (War doch Heap, oder?)
Damit wäre das von RapidMax erwähnte Problem mit mmap aus dem Weg.
Ob es eine bessere Lösung gibt weiss ich auch nicht. Aber ich denke auf diesem oder einem ähnlichen Weg kannst du recht gut arbeiten, weil "nicht dynamisch allokierte Variablen" meißt nur einen kleinen Teil ausmachen und berechenbar sind.
Sollte ich einen Fehler gemacht haben, bitte ich dies zu entschuldigen und zu korrigieren :)
Kai
RapidMax
04-05-2006, 10:09
Was für mich eine Lösung wäre, wäre die Funktionssammlung zur Speicherverwaltung (malloc und so) alle in neue Funktionen zu kapseln (oder ähnlich).
Als primitives Beispiel:
int UsedMemory = 0; // Speicherzähler global damit man mit allen Speicherfunktionen den erhöhen kann - static reicht net
void *MyMalloc(size_t size)
{
UsedMemory += size;
return malloc(size);
}
Beim malloc() zu zählen ist kein Problem, um aber die freigegeben Ressourcen von UsedMemory wieder abzuzählen ist etwas komplizierter:
Selber eine Liste führen (pointer -> size)
Mit Hilfe von malloc_usable_size() die Grösse ermitteln (Achtung, kann grösser als der vorher bei malloc() angegeben Wert sein!)
Sich selber durch die malloc()-Strukturen auf dem heap hangeln (sehr implementationsabhängig und aufwändig)
Aber wie schon erwähnt, gibt es dafür Libraries, allerdings sind die oft nur für Memory-Debugging Zwecke ausgelegt und wirken sich schlecht auf die Performance aus.
Gruss, Andy
Powered by vBulletin® Version 4.2.5 Copyright ©2025 Adduco Digital e.K. und vBulletin Solutions, Inc. Alle Rechte vorbehalten.