mallocierten Speicher mit free freigeben - ein Muss?
-
Hallo!
Die Frage im Titel bezieht sich auf das folgende Beispiel:
int main (void) { char* p = malloc (1000000); return 0; }
Das ist natürlich ein stark vereinfachtes Bsp.
Muss man free(p) aufrufen oder kann man sich darauf verlassen, das der Speicher vom Betriebssystem freigegeben wird?Gruß,
f.n.
-
Das kommt wahrscheinlich ganz auf Deinen Compiler / Linker an, ggf. auch aufs Betriebssystem. Was hält Dich denn davon ab, den Speicher wieder freizugeben?
-
es gibt einige funktionen, in denen der speicher lokal in schleifen reserviert wird und in einem fehlerfall wird exit aufgerufen.
ich müsste alle lokalen variablen, die speicher reservieren, freilegen und globalisieren.
-
Du musst free aufrufen.
-
free n00b schrieb:
.
Muss man free(p) aufrufenja, ohne wenn und aber.
free n00b schrieb:
.
oder kann man sich darauf verlassen, das der Speicher vom Betriebssystem freigegeben wird?nein.
Ein Auto ohne Bezin fährt nicht. Wieso bremsen, wenn das Auto sowieso stoppt, wenn ihm das Benzin ausgeht?
Du gibst nicht nur am Ende des Programms den Speicher frei sondern, wenn du ihn nicht mehr brauchst, dadurch kannst du Ressourcen freigeben und andere Prozesse profitieren (und letztendlich dein Programm auch) nur davon.
-
ich habe in manchen programm-dokumentationen gelesen, das betriebssysteme heapspeicher selbständig freigeben und das deshalb kein free aufgerufen werden muss!
-
c-doku-leser schrieb:
ich habe in manchen programm-dokumentationen gelesen, das betriebssysteme heapspeicher selbständig freigeben und das deshalb kein free aufgerufen werden muss!
ja, das stimmt. aber wenn man 'free' trotzdem aufruft, dann schadet es nichts. deshalb wird ja hier gesagt, dass man's machen muss, denn ein OS, das den müll seinen toten prozesse selbständig wegmacht, ist eigentlich ein sonderfall.
-
c-doku-leser schrieb:
ich habe in manchen programm-dokumentationen gelesen, das betriebssysteme heapspeicher selbständig freigeben und das deshalb kein free aufgerufen werden muss!
Das ist falsch. Wenn ein Betriebssystem das macht, dann macht es das nur, sobald das Programm beendet wurde. D.h. aber, dass deinem Programm unter Umständen schon der Speicher ausgegangen ist, weil es immer nur
malloc
und keinfree
aufruft! Verwende immerfree
wenn du Speicher allokierst.
-
Wenn dein Programm nur auf Windows oder Linux laufen soll und nicht auf irgendwelchen leightweight Microcontroller OS o.ä., dann kannst du free() weglassen! Wie du ja schon richtig sagtest, gibt Windows das alles wieder frei, wenn der Prozess endet. free() aufzurufen ist also vergebene Liebesmüh.
-
ProgChild schrieb:
c-doku-leser schrieb:
ich habe in manchen programm-dokumentationen gelesen, das betriebssysteme heapspeicher selbständig freigeben und das deshalb kein free aufgerufen werden muss!
Das ist falsch. Wenn ein Betriebssystem das macht, dann macht es das nur, sobald das Programm beendet wurde.
so meint er's doch bestimmt. 'nen automatischen garbage collector gibts ja nicht in C. wäre ja auch nicht besonders sinnvoll, bei 'ner low-level sprache.
Bernibutt schrieb:
Wenn dein Programm nur auf Windows oder Linux laufen soll und nicht auf irgendwelchen leightweight Microcontroller OS o.ä., dann kannst du free() weglassen!
quatsch mit soße. mach mal in 'ner schleife: *char p = malloc(irgendwas_ungleich_null); das geht nicht lange gut.
-
Bernibutt schrieb:
Wenn dein Programm nur auf Windows oder Linux laufen soll und nicht auf irgendwelchen leightweight Microcontroller OS o.ä., dann kannst du free() weglassen! Wie du ja schon richtig sagtest, gibt Windows das alles wieder frei, wenn der Prozess endet. free() aufzurufen ist also vergebene Liebesmüh.
unglaublich wie manche Programmier denken, kein Wunder, dass manche Windows-Programme das System zum Absturz bringen. Nochmal: man gibt nicht nur am Ende des Programm den Speicher frei, sondern wenn man ihn nicht mehr braucht. Das ist ein gewaltiger Unterschied!
-
Bitte lest den Beitrag des Threaderstellers doch einmal genauer. Dort war die Rede davon das Programm zu beenden! Da er ohnehin vorhat das Programm zu beenden, ist es also durchaus in Ordnung die überflüssigen aufrufe von free() einzusparen!
Nun ich weiß nicht, wie ihr aus der sehr deutlich formulierten Problembeschreibung irgendetwas von endlos Schleifen mit malloc() u.ä. herausgelesen habt. Vielleicht sei an dieser Stelle dem ein oder anderen eine Lesebrille empfohlen.
Ich bleibe bei meiner Meinung, du kannst dir die Aufrufe von free() ruhigen Gewissens einsparen!
-
und ich bei meiner, und ich hoffe, ich muss nie ein Programm von dir verwenden.
Es geht ums Prinzip! Klar kann man die Arbeit jemand anders überlassen, aber das ist ein schlechter Stil und führt dazu, dass man sich schlechte Angewohnheiten aneignet. Wenn der OP warum auch immer für ein OS Programme schreiben muss, welches diese Arbeit nicht abnimmt, dann steht man erstmal dumm da, wenn das System keine Ressourcen mehr frei hat. Man muss einfach ordentlich programmieren.
-
Etwas flasch zu machen, von dem man es nicht besser weiss, das kann passieren. Aber etwas gegen besseren Wissens falsch zu machen, ist Dummheit, Faulheit oder irgendeine andere Form eines charkterlichen Defizits.
-
es ist nicht falsch. solange man sich der umgebung, unter der das programm ausgeführt wird, bewußt ist, kann man diese auch entsprechend ausnutzen.
-
Das wäre dann aber kein portables C-Programm, bzw. allenfalls ein portables C-Programm mit einem Memory-Leak. Der Standard garantiert an keiner Stelle, dass gemallocter Speicher bei Programmende freigegeben wird, im Gegensatz z.B. zu geöffneten Dateien, die bei normaler Programmbeendigung geschlossen werden.
-
Kein unübliches Szenario, ohne OS und doppelten Boden:
Mein Programm startet, liest sich seine Parametrierung aus einem EEPROM oder von einer SD- Card und bastelt sich erstmal einen Satz Lookup- Tables. Da es von den Parametern abhängt, wie groß die werden, werfe ich das Zeug auf den Heap, wo es einfach verbleibt - ich brauche die Daten zur Runtime ja immer wieder.
Ein paar Geschichten davon habe ich als Simulation auf dem PC, da wird im Debug- Mode beim Beenden (weiters folgenlos) gemotzt, daß MemoryLeaks existieren, aber auch im Release- Mode wird unter Win und Linux immer der Speicher aufgeräumt. Da bleibt das fehlende free() folgenlos.
Ohne OS habe ich auch schon mal separat compilierte Binaries zusammengepackt, aber da interessiert sich die eine für die andere nicht, jede macht sich ihren eigenen Heap bereit, egal, weil sie in aller Regel nicht gemeinsam laufen müssen, da bräuchte man sowieso einen Scheduler und den ganzen Multitasking- Klimbim.Ich bin mal fürchterlich geschimpft worden, weil ich beim Powerdown den Heap nicht entrümple - wozu auch? Half nichts, ich mußte nachbasteln. Beim Flicker/Blackout/Brownout- Test gab's jedoch keinen Unterschied der Versionen.
Huh, mich stört das Genörgel auf MemoryLeaks schon so, daß ich sowas mit entsprechenden "kill"- Aufrufen wegmache, aber nur, wenn sich der Debugger drüber aufregt oder das OS den Kontext der Applikation nicht sauber aufräumen kann. Auf einem Controller ohne OS ist das eher sinnfreies Maschinenballett - wurscht, ob es aufgeführt wird oder nicht, schaut eh' niemand zu.
-
Japs, muss sein, sonst wird der Platz nicht freigegeben, d.h. dein Programm braucht auch nach dem beenden noch MB´s.
Achja, und nochwas, wenn eine Variable damit mehr Speicher als vorhanden zugeschrieben wird, wird der Speicher vom Datentyp verwendet.
Das heißt eine "int *a=cmalloc(1,9999999...9999")" Variable hat am ende, wennst sehr viele 9er machst auch nur 4 Bytes...
mfg
EDIT:
habe gerade gesehen, dass du es mit dem normalen MALLOC machst...
na dann nicht! malloc legt nur lokal speicher an, also Programm aus=Speicher weg
-
VirusMaker schrieb:
Achja, und nochwas, wenn eine Variable damit mehr Speicher als vorhanden zugeschrieben wird, wird der Speicher vom Datentyp verwendet.
Das heißt eine "int *a=cmalloc(1,9999999...9999")" Variable hat am ende, wennst sehr viele 9er machst auch nur 4 Bytes...
So ein Unfug, wenn es keinen freien Speicher mehr gibt, gibt malloc NULL zurück.
-
namespace invader schrieb:
Das wäre dann aber kein portables C-Programm, bzw. allenfalls ein portables C-Programm mit einem Memory-Leak. Der Standard garantiert an keiner Stelle, dass gemallocter Speicher bei Programmende freigegeben wird
Der Standard kann darüber auch keine Aussage machen, weil es nicht in sein Gebiet fällt. Dazu müsstest du schon Posix oder dergleichen heranziehen.