Sehr freakig, hut ab.![]()
Hab noch ein bisschen damit rumgespielt und muss sagen, es ist richtig cool. Lege ich jedem ans Herz, der ein bisschen Ahnung von OpenGL und eine Webcam hat.
Btw: Muss ich mir Gedanken machen, wenn mich Luki bittet, eine RPG Maker 2003 Map für ihn zu bearbeiten und ich einen Hexeditor nehme, statt den passenden Maker zu installieren?
--
Mir war nichtmal bewusst dass ich nominiert wurde, aber: Cool! Hälfte des Lobes muss aber unbedingt an Archeia!Now all new and shiny:CherryShare | Patches und Tools | Programmwunschthread | www.cherrytree.at | Cherry = CherryDT
Ähnliches, hervorgerufen durch copy & paste, ist mir vor kurzem in einem größeren Programm mit Dateioperationen passiert. Glücklicherweise aber schnell entdeckt.![]()
Mein C ist nicht so wirklich gut, aber lese ich richtig das "&Buffer" das Problem ist? Weil es ist ja ein Pointer und soZitat
calloc() macht doch das selbe, was du gemacht hast.
Naja, solange du den Speicher nicht genullt brauchst, ist calloc() halt unnötiger Mehraufwand. Andernfalls ist's aber echt eine gute Frage. ^^" Gewohnheit wohl, und die Tatsache, dass es meist nicht viel Unterschied macht, performanztechnisch.
@ Whiz: Er hat ja geschrieben, "Ähnliches", ist im Original also vielleicht eh sinnvoller, bzw. nicht der Punkt.
--A human is a system for converting dust billions of years ago into dust billions of years from now via a roundabout process which involves checking email a lot.
Ich denke, das hat wohl was damit zu tun, dass C für Unix gedacht war und Unix generell den Speicher mit Nullen belegt. Da macht es keinen Unterschied, ob malloc() oder calloc(). Nur unter Windows muss man da höllisch aufpassen. Auch wenn man den Speicher nicht genullt braucht, würde ich es dennoch machen. Schaden kann es nicht.
Daß malloc() den Speicher nullt ist auch unter Unix nicht garantiert. Die meisten oder alle neueren Unixe machen es zwar so, aber garantiert ist es absolut nicht.
Naja, der Zeitbedarf ist doch recht minimal, sodass man ihn schon quasi vernachlässigen kann.
Der Zeitunterschied zwischen den beiden Funktionen, bei 1.000.000 Blöcken a 1 MB Plus Freigeben des Speichers liegt, bei meinem Rechner, bei 124 ms.
Ich besitze einen Intel C2D E6600 (2x 2,4 Ghz) und 2 GB RAM.
Da gibt es eigentlich kein Optimierungspotenzial.
hab jetzt mal alle Programme geschlossen und mein Testprogramm durchlaufen lassen.
nun liegt der Unterschied sogar bei nur 47 ms.
Zitat
Ja, richtig. Die interessantere Frage ist aber nicht wo die Ursache ist, sondern was genau dabei passiert. Da es eine lokale Variable auf dem Call Stack ist, wird dieser überschrieben und damit alle im Stack folgenden Rücksprungadressen, Funktionsparameter, etc. Kurz gesagt, Katastrophe. In diesem Fall ist es sogar noch schlimmer, da ohne Debugger das Programm an der Stelle der früher oder später resultierenden Zugriffsverletzung still beendet ("bla bla" wird nicht ausgegeben), ohne auf das Fehlverhalten mit einer entsprechenden Ausnahmebehandlung zu reagieren.
Ursprünglich war es wie erwähnt eine Dateioperation, fread um genau zu sein. memset sollte wirklich nur dem Vorführungszweck dienen.
Da würden dir die C-Entwickler vermutlich etwas anderes sagen. Redundanz im Zeichen der Fehlerreduzierung entspricht zum Beispiel nicht der C-Philosophie.
Die Frage, ob man auf malloc verzichten sollte erinnert mich an die Frage, ob man auf goto verzichten sollte. Hierzu:
Besonders in C hat goto einen festen Platz und vereinfacht oft den Code, wie zum Beispiel in der Ausnahmebehandlung. Ähnlich verhält es sich mit malloc und calloc. Beide haben Vor- und Nachteile, die je nach Situation andere Gewichtung haben können. Verdammen ist ist in meinen Augen nie gut und schädlicher als fragliche Anwendung.Zitat
Ohne Code sind diese Resultate nicht wirklich repräsentativ. Man kann auf eine Weise messen und auf eine andere mit jeweils völlig unterschiedlichen Ergebnissen. Entscheidend wären beispielsweise, Granularität, Mittelwertbildung mehrerer Messwerte um Abweichungen durch Interrupts und ähnliches zu minimieren, Reduzierung auf die Messung der tatsächlichen Arbeit (free ist ein Störfaktor), usw.
Ich habe mal einige Messungen auf meinem Pentium D 2.8 Ghz gemacht und bei mir braucht malloc für 1 MB im Schnitt (10 Messungen hintereinander) etwa 12500 clock cycles (entspricht etwa 4.46 us bei 2.8 Ghz) und calloc etwa 13500 clock cycles (etwa 4.82 us). Damit ist calloc um 8% langsamer als malloc. Nicht viel, aber viel hat man hier auch nicht erwartet, denn Nullsetzung ist sehr billig und in heutigen Zeiten in der Regel SIMD-optimiert. Natürlich erhebe ich keinen Anspruch, dass auch meine Messungen 100%-ig repräsentativ und fehlerfrei sind. Jedenfalls gibt es einen Unterschied, der in manchen Situationen sogar größer sein kann und damit eventuell abgewogen werden könnte, wie zum Beispiel auf Systemen ohne SIMD, wenigen und kleinen Caches etc.
Geändert von Kyuu (16.02.2010 um 23:04 Uhr)
Stellt sich die Frage, ob du auch noch sprintf() benutzt. Das ist ja bekanntermaßen eine gute Möglichkeit, unkontrolliert Speicher zu überschreiben und viele empfehlen, stattdessen snprintf() (bei C99-fähigen Compilern) oder asprintf() (bei GNU GCC) zu verwenden. Zugegeben, die sind vermutlich beide langsamer, aber solange man nicht per (semi-)formellem Beweis nachweisen will, daß der Puffer nicht überlaufen kann, stellen sie auch Schutz vor einem potentiellen Sicherheitsrisiko dar.
Hängt von den Softwarekriterien ab.