2010-12-27 9 views
1

Ich habe Probleme beim Freigeben von Speicher, den ich mithilfe von malloc zugewiesen habe. Das Programm läuft gut bis es der Teil ist, in dem es freigegeben werden soll. Hier friert das Programm ein. Also habe ich mich gefragt, was das Problem sein könnte, da ich gerade C lerne. Syntaktisch scheint der Code korrekt zu sein, also könnte es sein, dass ich alle Sachen an diesem Ort löschen muss, bevor ich Speicher von diesem Ort oder etwas anderem freigebe?Problem beim Freigeben von Speicher mithilfe von free()

Hier ist der Code.

// Program to accept and print out five strings 
#include <stdio.h> 
#include <stdlib.h> 
#include <string.h> 

#define NOOFSTRINGS 5 
#define BUFFSIZE 255 

int main() 
{ 
    char buffer[BUFFSIZE];//buffer to temporarily store strings input by user 
    char *arrayOfStrngs[NOOFSTRINGS]; 
    int i; 

    for(i=0; i<NOOFSTRINGS; i++) 
    { 
     printf("Enter string %d:\n",(i+1)); 
     arrayOfStrngs[i]=(char*)malloc(strlen(gets(buffer)+1));//calculates string length and allocates appropriate memory 
     if(arrayOfStrngs[i] != NULL)//checking if memory allocation was successful 
     { 
      strcpy(arrayOfStrngs[i], buffer);//copies input string srom buffer to a storage loacation 
     } 
     else//prints error message and exits 
     { 
      printf("Debug: Dynamic memory allocation failed"); 
      exit (EXIT_FAILURE); 
     } 
    } 

    printf("\nHere are the strings you typed in:\n"); 
    //outputting all the strings input by the user 
    for(i=0; i<NOOFSTRINGS; i++) 
    { 
     puts(arrayOfStrngs[i]); 
     printf("\n"); 
    } 

    //Freeing up allocated memory 
    for(i=0; i<NOOFSTRINGS; i++) 
    { 
     free(arrayOfStrngs[i]); 
     if(arrayOfStrngs[i] != NULL) 
     { 
      printf("Debug: Memory deallocation failed"); 
      exit(EXIT_FAILURE); 
     } 
    } 

    return 0; 
} 
+1

Klassische Fehler sein. Code in mehr als eine Zeile zu setzen kostet nichts mehr. Außerdem kann gets() NULL, kaboom zurückgeben. –

+2

!!! Verwende niemals 'gets()'. Je. BTW, Ihre Fehlerberichterstattung ist falsch: das Aufrufen von 'free' ** beeinflusst nicht den Wert des übergebenen Zeigers - das ist ** nicht möglich ** in C, ohne eine weitere Ebene der Indirektion hinzuzufügen, die 'frei' nicht. Selbst wenn der Speicher erfolgreich freigegeben wurde, denkt Ihr Programm, dass dies nicht der Fall ist. –

Antwort

4

Sie mißbrauchen strlen() und dies führt zu Pufferüberlauf:

arrayOfStrngs[i]=(char*)malloc(strlen(gets(buffer)+1)); //pointer from gets() is incremented and passed to strlen() - that's wrong 

sollte
arrayOfStrngs[i]=(char*)malloc(strlen(gets(buffer))+1); //pointer from gets() is passed to strlen(), then returned value is incremented - correct 

auch free() nicht die an sie übergebenen Zeiger ändern. So dass

char* originalValue = pointerToFree; 
free(pointerToFree); 
assert(pointerToFree == originalValue); //condition will always hold true 

und so in Ihrem Code befreien Speicher sollte nur sein

//Freeing up allocated memory 
for(i=0; i<NOOFSTRINGS; i++) 
{ 
    free(arrayOfStrngs[i]); 
} 
+0

Vielen Dank. Ich kannte mich tatsächlich nicht frei() sehr gut, so dass Tipp auf frei() den Wert des Zeigers nicht zu verändern, erleuchtend war. Du hattest Recht. Der Pufferüberlauf war die Ursache des Problems, aber ich habe vergessen, etwas in die obige Frage aufzunehmen, und ich wäre Ihnen dankbar, wenn Sie auch bei diesem Problem helfen würden. Wie kommt es, dass der Array-Puffer von all seinen vorherigen Daten "bereinigt" wird, bevor gets() Daten vom Benutzer hineingibt, ohne dass der Programmierer dies spezifiziert? –

+2

"Wie ist es, dass der Array-Puffer von all seinen vorherigen Daten" bereinigt "wird, bevor gets() Daten vom Benutzer hineingibt, ohne dass der Programmierer dies spezifiziert?" ** Es ist nicht **. Es muss nicht sein. Die vorherigen Daten werden überschrieben. –

2
arrayOfStrngs[i]=(char*)malloc(strlen(gets(buffer)+1));//calculates string length and allocates appropriate memory 

Sollte das nicht

arrayOfStrngs[i]=(char*)malloc(strlen(gets(buffer))+1); 
+0

Ja, genau. Die aktuelle Implementierung verfügt über einen Pufferüberlauf. – sharptooth

+0

Und eine sehr coole - eine +1, die als -1 fungiert. –

Verwandte Themen