2011-01-22 4 views
2

Je cours valgrind pour rechercher des fuites de mémoire. J'ai alloué deux variables globales dans la fonction principale; puis, à la fin de main je libre à la fois, mais Valgrind écrit motive:Valgrind et variables globales

==18311== 16 bytes in 1 blocks are definitely lost in loss record 1 of 2 
==18311== at 0x4025BD3: malloc (vg_replace_malloc.c:236) 
==18311== by 0x804A30C: main (application.c:730) 
==18311== 
==18311== 16 bytes in 1 blocks are definitely lost in loss record 2 of 2 
==18311== at 0x4025BD3: malloc (vg_replace_malloc.c:236) 
==18311== by 0x804A31D: main (application.c:731) 

Résumé des fuites:

==18311== LEAK SUMMARY: 
==18311== definitely lost: 32 bytes in 2 blocks 
==18311== indirectly lost: 0 bytes in 0 blocks 
==18311==  possibly lost: 0 bytes in 0 blocks 
==18311== still reachable: 0 bytes in 0 blocks 
==18311==   suppressed: 0 bytes in 0 blocks 

Pourquoi je ne peux pas libérer ces deux variables?

Modifier

someList *something; *something_else; 

La structure utilisée comporte deux champs de type et un champ char *someList *next. Plus tard, il y a beaucoup de code. Quelques threads vont ajouter/modifier/supprimer des objets en utilisant ces deux variables.

something -> object 1 -> ... -> object n 
something_else -> object 1 -> ... -> object m 

-> signifie que something->next = object 1 et object k sont toutes les instances de someList *.

Vers la fin de l'application, j'ai libéré tous les champs de chaque élément object k. Puis, dans la dernière partie:

free(something); 
free(something_else); 

Il est possible que j'ai oublié de libérer un champ d'un objet. Cela peut-il causer le comportement que j'ai ici?

J'espère que c'est plus clair maintenant. Etes-vous sûr de vouloir désallouer toutes vos variables?

+0

La partie du code dans laquelle vous les libérez est-elle exécutée? Un retour anticipé de la fonction principale peut l'ignorer. – CodesInChaos

+1

Besoin de voir le code. – SoapBox

+0

@CodeInChaos oui: le code est exécuté. Merci quand même. – Donovan

Répondre

0

Pour chaque appel , vous avez généralement besoin d'un appel free() correspondant, afin d'éviter les fuites de mémoire. Pour une utilisation optimale de la mémoire, vous devez free() alloué chaque bloc de mémoire dès que possible après avoir terminé avec elle.

Dans votre cas, vous avez deux malloc() appels à application.c:730 et application.c:731, pour lesquels il n'y a pas free() appel lancé par le temps que votre programme se termine. Par conséquent, les blocs de mémoire alloués là ne sont pas libérés. Cela provoque une fuite de mémoire qui Valgrind détecte et signale.

À moins que vous nous fournissiez du code et/ou plus d'informations sur votre programme, nous n'avons aucun moyen de vous aider davantage.

EDIT:

Il y a deux lignes intéressantes dans votre Valgrind sortie:

==18311== definitely lost: 32 bytes in 2 blocks 
... 
==18311== still reachable: 0 bytes in 0 blocks 

Vous avez certainement « perdu » deux blocs de mémoire et il ne pointeurs vers les au moment où votre programme se termine. Cela signifie que les pointeurs vers ces deux blocs ont en fait été écrasés ou ont perdu leur valeur au cours de votre programme.Une cause courante de ce problème est le stockage du résultat de deux appels malloc() sur le même pointeur sans appel intermédiaire free(). Une autre cause possible est une valeur de pointeur modifiée en raison des opérations arithmétiques de pointeur - Valgrind fait un effort pour détecter certains de ces cas, mais il ne réussit pas toujours, selon votre code.

+0

Gardez à l'esprit la première phrase de cette réponse est sur l'idée de valgrind des fuites de mémoire et non de l'utilisateur. Dans l'œil de tout utilisateur, un programme de longue durée qui ne libère jamais rien jusqu'à ce que juste avant la sortie a une énorme fuite de mémoire, alors que dans les yeux de valgrind n'a pas de fuite. Inversement, un programme de ligne de commande unique qui fait sa tâche et qui ne libère jamais rien n'a aucune fuite de mémoire aux yeux de l'utilisateur, mais il le fait dans valgrind. –

+0

@R ..: J'ai reformulé la réponse un peu pour couvrir un peu ce point. – thkala

+0

Donc, d'après ce que je comprends après avoir lu ceci, les variables globales n'ont-elles PAS besoin d'être libérées? Est-ce une hypothèse sûre? Dites avec une déclaration de 'char mychar [80];' <- situé en dehors de main (global) –

1

Valgrind dit que tu ne l'es pas. Essayez d'alléger votre code et publiez-le ici, ou lancez un peu plus de débogage.