2009-08-05 10 views
1

Ich habe ein Programm, das eine Funktion mit undefinierten Argumente nennen, wie folgt aus:C/Glib Memory Management {keine baumelnden Referenz> WHYY ??!}

#include <stdargs.h>
... /* code */ int main() {
GArray *garray = g_array_new (FALSE, FALSE, sizeof (char *)); /* the code above initialize the GArray, and say that the garray expect a pointer to char. */
function_name (garray, "arg2", "arg3" /* and so on ... */);
... /* code */ }

zur Kenntnis, dass die args zwischen "" Strings in der Funktion _ Namen, so:

static void function_name (GArray *garray, ...) { 
    ... /* code */ 
    char *data;
data = va_arg (garray, gchar *); g_array_append_val (garray, data);
... /* code */ }

      also, wenn Datenpunkte auf ein Argument in va_list, wenn die Funktion Rückkehr, teorically die Daten darauf, schalten für ungültig erklärt werden, und in garray auch.
(verursacht eine freie Referenz, da der Datenzeiger auf eine Speicheradresse zeigt, die nicht mehr reserviert ist).

      aber es scheint nicht zu passieren, das Programm läuft gut. Warum? und in C werden Argumente, die an Funktionen übergeben werden, im Stapel gespeichert, so dass die Datenpunkte tatsächlich im Speicher liegen.

thnkx viel.

Antwort

5

Wenn Sie in einem C-Programm eine String-Konstante einfügen, wird ein unbenanntes, nicht änderbares Objekt mit statischer Speicherdauer erstellt. "Statische Speicherdauer" bedeutet, dass es für die Lebensdauer des Programms lebt.

Also, wenn Sie diese in Ihrem Code:

function_name (garray, "arg2", "arg3" /* and so on ... */); 

Die Saiten "arg2" und "arg3" String-Konstanten sind - sie existieren irgendwo im Programmspeicher, für das Leben des Programms. Oft sind diese in einem Textsegment gespeichert, genau wie der Programmcode selbst.

Was eigentlich an funktionsname() übergeben wird - vermutlich auf dem Stapel - sind Zeiger auf diese String-Konstanten. Und das ist, was Ihr GArray am Ende speichert - Zeiger auf diese String-Konstanten.

(Beachten Sie, dass eine als Arrayinitialisierer verwendete Zeichenfolge nicht eine Zeichenfolgenkonstante ist).

+0

Sie sagten 'Objekt mit statischer Speicherdauer ist erstellt', das wusste ich nicht, thnx caf, das erklärt meine Zweifel! D – drigoSkalWalker

0

Einer von drei Dinge erfüllt sind:

Entweder: 1) g_array_append_val ist eine Kopie des Strings zu machen.

Oder: 2) Sobald der Stapel wieder überschrieben wird, werden die Dinge brechen.

void burn_stack(int size) 
{ 
    char data[8]={0,0,0,0,0,0,0,0}; 
    size-=8; 
    if (size>0) burn_stack(size); 
} 

Versuchen Sie, burn_stack (256) aufzurufen; Nach Funktionsname, und sehen, ob die Dinge weiter funktionieren.

Oder: 3) Sie verwenden const char "string" s, die im String-Abschnitt der ausführbaren Datei gespeichert sind, und nicht auf dem Heap noch den Stapel, daher werden sie auf unbestimmte Zeit beibehalten.

+0

Falsch - diese Zeichenfolgenkonstanten haben eine statische Speicherdauer, sodass sie wahrscheinlich nicht auf dem Stapel gespeichert werden. Die Hinweise darauf sind wahrscheinlich, aber das ist hier kein Problem. – caf

+1

Ah natürlich sind sie Konstanten. Mein Fehler. –

Verwandte Themen