free struct ptr



  • Hallo,

    ist es eigentlich möglich, wenn man innerhalb einer struct mehrere items hat, die ihren speicher mittels malloc erhalten haben, durch free(struct) zu löschen?

    typedef struct beispiel {
    
     unsigned char *ptr1; 
     unsigned char *ptr2; 
    }BSP; 
    
    BSP.ptr1 = (unsigned char *)malloc(sizeof("hallo"));
    memcpy(bsp.ptr1....); 
    BSP.ptr2 = (unsigned char *)malloc(sizeof("irgnedwas_anderes")); 
    memcpy(bsp.ptr2...); 
    
    //kann man jetzt einfach schreiben
    free(BSP); 
    
    //oder muss man
    free(BSP.ptr2); 
    free(BSP.ptr1);
    

    mfg
    markus



  • bis jetzt bekomm ich bei

    free(BSP);
    

    immer die fehlermeldung "cannot convert parameter l from BSP to void *" - aber ich hab gar keinen void *ptr innerhalb der struct stehen...

    markus



  • markus kaulich schrieb:

    //kann man jetzt einfach schreiben
    free(BSP); 
    
    //oder muss man
    free(BSP.ptr2); 
    free(BSP.ptr1);
    

    mfg
    markus

    Du musst schon dem free() die gleiche Adresse angeben, wie malloc sie dir
    gegeben hat. Also ist der zweite Fall korrekt und der erste schlägt fehl.

    Gruß mcr



  • Faustregel: für jeden malloc muss es ein free geben.

    Frage: hast du mit malloc Speicher für 'BSP' reserviert?
    Antwort: Nein, also free(BSP) ist nicht notwendig. Außerdem ist BSP kein Zeiger.

    Du hast 2 malloc Aufrufe jeweils für BSP.ptr1 und BSP.ptr2 verwendet, also brauchst du einen free Aufruf für jeweils BSP.ptr1 und BSP.ptr2.



  • äääh, und diese casts vor malloc .....
    naja, ihr wisst schon.
    🙂



  • void*-freak schrieb:

    äääh, und diese casts vor malloc .....
    naja, ihr wisst schon.
    🙂

    wenn ich diese casts nicht mache, bekomme ich dauernd warnungen angezeigt von visual c++.

    Du hast 2 malloc Aufrufe jeweils für BSP.ptr1 und BSP.ptr2 verwendet, also brauchst du einen free Aufruf für jeweils BSP.ptr1 und BSP.ptr2.

    ich brauch dann auch zwei free aufrufe, oder kann ich die hintereinander in free eintragen?

    markus



  • markus kaulich schrieb:

    wenn ich diese casts nicht mache, bekomme ich dauernd warnungen angezeigt von visual c++.

    dann kompiliere deinen C Code mit einen C Compiler und nicht mit einem C++ Compiler 🙄

    markus kaulich schrieb:

    ich brauch dann auch zwei free aufrufe, oder kann ich die hintereinander in free eintragen?

    natürlich brauchst du zwei Aufrufe. Siehe meine Faustregel und mcrs Antwort!



  • markus kaulich schrieb:

    typedef struct beispiel {
    
     unsigned char *ptr1; 
     unsigned char *ptr2; 
    }BSP; 
    
      
    BSP.ptr1 = (unsigned char *)malloc(sizeof("hallo"));
    memcpy(bsp.ptr1....); 
    BSP.ptr2 = (unsigned char *)malloc(sizeof("irgnedwas_anderes")); 
    memcpy(bsp.ptr2...); 
    
    //kann man jetzt einfach schreiben
    free(BSP);
    

    mit nur einem malloc/free könnte es so gehen:

    BSP.ptr1 = malloc(sizeof("hallo") + sizeof("irgnedwas_anderes"));  // <-- ein malloc
    memcpy(bsp.ptr1....); 
    BSP.ptr2 = BSP.ptr1  + sizeof("hallo"); // <-- speicher aufteilen
    memcpy(bsp.ptr2...); 
    ...
    free (BSP.ptr1);  // <-- ein free
    // free ((void*)*(ptrdiff_t*)&BSP);  // <--- oder so
    

    🙂



  • nette Spielereien zum Angeben, aber was ist wenn das Struct so aussieht? 😉

    typedef struct beispiel {
     double value;
     struct beispiel *next;
     unsigned char *ptr1; 
     unsigned char *ptr2; 
    }BSP;
    

    @markus: die Spielerei von *-freak ist zwar nett und zeigt sowohl die Stärken als auch die Schwächen von C. Jedoch rate ich davon ab, sowas zu benutzen, denn es gibt keinen Vorteil und man kann mehr Fehler machen, als wenn man einfach

    free(BSP.ptr1); 
    free(BSP.ptr2);
    

    macht und außerdem ist der Code so auch um einiges lesbarer.



  • supertux schrieb:

    nette Spielereien zum Angeben, aber was ist wenn das Struct so aussieht? 😉

    typedef struct beispiel {
     double value;
     struct beispiel *next;
     unsigned char *ptr1; 
     unsigned char *ptr2; 
    }BSP;
    

    ...dann klappt das free (BSP.ptr1) immer noch, weils ja der rückgabewert des einzigen 'mallocs' ist. aber klar, das free ((void)(ptrdiff_t)&BSP)* ist nur als spass zu sehen und in einem richtigen programm sollte man solchen unsinn natürlich sein lassen.
    🙂



  • mir ging's tatsächlich nur um den zweiten free Aufruf, der würde so nicht klappen. Klar weiß ich, dass du das als Spaß betrachtest, aber Anfänger oder nicht erfahrene Einsteiger verstehen/sehen das nicht als Spaß und denken, es ist ernst gemeint und bauen sowas ein und wundern sich danach, warum es kracht.


Anmelden zum Antworten