IdentifiantMot de passe
Loading...
Mot de passe oublié ?Je m'inscris ! (gratuit)
Navigation

Inscrivez-vous gratuitement
pour pouvoir participer, suivre les réponses en temps réel, voter pour les messages, poser vos propres questions et recevoir la newsletter

C++ Discussion :

[C++ Standard] Pourquoi ai je une fuite de mémoire ?


Sujet :

C++

  1. #1
    Membre régulier
    Profil pro
    Inscrit en
    Avril 2007
    Messages
    113
    Détails du profil
    Informations personnelles :
    Localisation : France, Sarthe (Pays de la Loire)

    Informations forums :
    Inscription : Avril 2007
    Messages : 113
    Points : 99
    Points
    99
    Par défaut [C++ Standard] Pourquoi ai je une fuite de mémoire ?
    Bonjour à tous,
    j'ai une application qui ne fait pas de "new" en dehors de la période d'initialisation. A priori vu que je ne manipule que des données déjà existantes y a pas de raison que ma mémoire soit grignotée petit à petit.

    j'ai déjà vérifié, ce n'est pas un de mes vecteurs qui augmentent de taille.

    qu'est ce qui peut provoquer une fuite de mémoire ?
    je me souviens plus comment on fait pour connaître la mémoire alloué par le programme quand on a que la STL et posix a sa disposition...

    Vincent

  2. #2
    Membre éclairé
    Avatar de Florian Goo
    Profil pro
    Inscrit en
    Septembre 2008
    Messages
    680
    Détails du profil
    Informations personnelles :
    Âge : 38
    Localisation : France, Paris (Île de France)

    Informations forums :
    Inscription : Septembre 2008
    Messages : 680
    Points : 858
    Points
    858
    Par défaut
    Bonjour,

    Peux-tu nous expliquer plus en détail ce que fait ton programme ?
    Une augmentation de la mémoire allouée ne signifie pas forcément une fuite mémoire. Cela peut provenir d'un buffer qui ne se vide pas, d'un empilage de données qui ne sont pas dépilées, …
    Cours : Initiation à CMake
    Projet : Scalpel, bibliothèque d'analyse de code source C++ (développement en cours)
    Ce message a été tapé avec un clavier en disposition bépo.

  3. #3
    Membre émérite
    Avatar de white_tentacle
    Profil pro
    Inscrit en
    Novembre 2008
    Messages
    1 505
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Novembre 2008
    Messages : 1 505
    Points : 2 799
    Points
    2 799
    Par défaut
    Tu n'appellerais pas des fonctions qui initialisent des handle sur des objets, et que tu oublies de libérer ?

  4. #4
    Membre régulier
    Profil pro
    Inscrit en
    Avril 2007
    Messages
    113
    Détails du profil
    Informations personnelles :
    Localisation : France, Sarthe (Pays de la Loire)

    Informations forums :
    Inscription : Avril 2007
    Messages : 113
    Points : 99
    Points
    99
    Par défaut
    Citation Envoyé par Florian Goo Voir le message
    Bonjour,
    Peux-tu nous expliquer plus en détail ce que fait ton programme ?
    En gros c'est un moteur de physique, j'ai un monde virtuel dans lequel je peux rajouter des objets 3D, le monde virtuel detecte les collisions possible, les résouds etc...
    J'ai une boucle qui se lance au début de chaque frame dans l'ordre :
    - tri des objets (pour baisser le nb de paire)
    - detection des pairs
    - résolution des pairs en collision

    Citation Envoyé par Florian Goo Voir le message
    Une augmentation de la mémoire allouée ne signifie pas forcément une fuite mémoire. Cela peut provenir d'un buffer qui ne se vide pas, d'un empilage de données qui ne sont pas dépilées, …
    c'est quoi un empilage de données ?

    Tu n'appellerais pas des fonctions qui initialisent des handle sur des objets, et que tu oublies de libérer ?
    je n'utilise pas de handle, juste des pointeurs et des reférences c'est tout.
    dis m'en plus sur les handles, je connais pas trop... je suis un vieu je connais pas la programmation windows :p

    Vincent, je ne fait que du C++ Orienté Objet dans cette bibliothèque, avec la STL et un peu de POSIX (mais ca bug même sans creer de thread)... comprend pas. Qui peut me rappeler comment on fait pour avoir la quantité de menoire pris par le programme en C/C++ non windows ?

  5. #5
    Membre éclairé
    Avatar de Florian Goo
    Profil pro
    Inscrit en
    Septembre 2008
    Messages
    680
    Détails du profil
    Informations personnelles :
    Âge : 38
    Localisation : France, Paris (Île de France)

    Informations forums :
    Inscription : Septembre 2008
    Messages : 680
    Points : 858
    Points
    858
    Par défaut
    Qui peut me rappeler comment on fait pour avoir la quantité de menoire pris par le programme en C/C++ non windows ?
    Non Windows ? C'est à dire que tu es sous Linux ?
    Sous Unix en général, il y a la commande top pour ça (avec l'option -p pour avoir un processus particulier). Mais je dois dire que je ne suis pas un spécialiste de la ligne de commande.

    Par empilage, je faisais référence à la pile système : http://fr.wikipedia.org/wiki/Allocation_de_mémoire

    Enfin, un handle, c'est un identifiant vers un objet alloué dynamiquement. C'est surtout utilisé en C. En C++, on subit ce genre de vieilleries quand on travaille directement avec l'API système (comme l'API Windows).

    Je dois reconnaitre que je ne sais pas quoi dire pour l'instant…
    Si j'étais à ta place, je réduirais mon code au fur et à mesure jusqu'à obtenir un exemple minimal, afin d'isoler le problème.
    Cours : Initiation à CMake
    Projet : Scalpel, bibliothèque d'analyse de code source C++ (développement en cours)
    Ce message a été tapé avec un clavier en disposition bépo.

  6. #6
    Membre averti
    Profil pro
    Inscrit en
    Janvier 2009
    Messages
    327
    Détails du profil
    Informations personnelles :
    Âge : 36
    Localisation : France, Bouches du Rhône (Provence Alpes Côte d'Azur)

    Informations forums :
    Inscription : Janvier 2009
    Messages : 327
    Points : 402
    Points
    402
    Par défaut
    Bonjour,

    c'est quoi un empilage de données ?
    Vous devriez faire quelques recherches sur les structures de données. C'est très instructif et passionnant. Pour débuter je te conseil ceci : Structure de données.

    je n'utilise pas de handle, juste des pointeurs et des références c'est tout.
    Je penses que c'est les pointeurs qui font des fuites de mémoire il faudrait que vous adoptiez une stratégie de gestion de mémoire efficace. Cf voir Ceci.

    dis m'en plus sur les handles, je connais pas trop...
    Voilà je trouves que cette article sur Wikipédia explique cela assez bien ici.

    Qui peut me rappeler comment on fait pour avoir la quantité de menoire pris par le programme en C/C++ non windows ?
    Désolé je n'en c'est rien, il faudra attendre quelqu'un qui est plus spécialisé que moi sur ce sujet.

    A bientôt

  7. #7
    Membre régulier
    Profil pro
    Inscrit en
    Avril 2007
    Messages
    113
    Détails du profil
    Informations personnelles :
    Localisation : France, Sarthe (Pays de la Loire)

    Informations forums :
    Inscription : Avril 2007
    Messages : 113
    Points : 99
    Points
    99
    Par défaut
    Citation Envoyé par Florian Goo Voir le message
    Non Windows ? C'est à dire que tu es sous Linux ?
    Je suis sous windows mais je fais du c++ standard, j'ai pas acces au API Windows...

    Citation Envoyé par Florian Goo Voir le message
    Par empilage, je faisais référence à la pile système
    a priori la pile se vide quand on quitte la fonction ou elle est utilisée.. je dois vérifier un truc quand même.

    Citation Envoyé par Florian Goo Voir le message
    Je dois reconnaitre que je ne sais pas quoi dire pour l'instant… Si j'étais à ta place, je réduirais mon code au fur et à mesure jusqu'à obtenir un exemple minimal, afin d'isoler le problème.
    C'est ce que je fais pour le moment ...

  8. #8
    Membre régulier
    Profil pro
    Inscrit en
    Avril 2007
    Messages
    113
    Détails du profil
    Informations personnelles :
    Localisation : France, Sarthe (Pays de la Loire)

    Informations forums :
    Inscription : Avril 2007
    Messages : 113
    Points : 99
    Points
    99
    Par défaut
    Citation Envoyé par wakan Voir le message
    Pour débuter je te conseil ceci : Structure de données.
    heu, je crois pas qu'on parle de la même chose la.

    Citation Envoyé par wakan Voir le message
    Je penses que c'est les pointeurs qui font des fuites de mémoire il faudrait que vous adoptiez une stratégie de gestion de mémoire efficace. Cf voir Ceci.
    j'ai préciser dans mon post initial que je ne faisais de new qu'au debut du programme et qu'il n'y a aucun autre new par la suite. donc en terme de fuite de mémoire ça ne pouvait pas être ca.


    Citation Envoyé par wakan Voir le message
    Voilà je trouves que cette article sur Wikipédia explique cela assez bien ici.
    pareil... on parle pas de handle de fichier mais de handle de programme...

  9. #9
    Rédacteur

    Avatar de ram-0000
    Homme Profil pro
    Consultant en sécurité
    Inscrit en
    Mai 2007
    Messages
    11 517
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 61
    Localisation : France, Haute Garonne (Midi Pyrénées)

    Informations professionnelles :
    Activité : Consultant en sécurité
    Secteur : High Tech - Opérateur de télécommunications

    Informations forums :
    Inscription : Mai 2007
    Messages : 11 517
    Points : 50 367
    Points
    50 367
    Par défaut
    Citation Envoyé par Fraggy Voir le message
    j'ai préciser dans mon post initial que je ne faisais de new qu'au debut du programme et qu'il n'y a aucun autre new par la suite. donc en terme de fuite de mémoire ça ne pouvait pas être ca.
    Toi tu ne fait pas de new mais peut être qu'insidieusement, il y a des new qui sont faits ailleurs dans le code (un vector ou une list qui grandit).

    Ce que tu peux faire si tu maitrise le code de l'application c'est de surcharger le new et le delete global et ainsi de tracer les appels avec les taille allouées. Cela ne marche que pour new et delete, pour les malloc et free, faudra trouver autre chose. Je ne sais pas si Valgrind ne sait pas faire de la détection de fuite mémoire.

    Dans le livre Penser en C++ traduit par l'équipe, il y a un exemple pour surcharger le new et le delete global (chapitre 13.5.1)
    Raymond
    Vous souhaitez participer à la rubrique Réseaux ? Contactez-moi

    Cafuro Cafuro est un outil SNMP dont le but est d'aider les administrateurs système et réseau à configurer leurs équipements SNMP réseau.
    e-verbe Un logiciel de conjugaison des verbes de la langue française.

    Ma page personnelle sur DVP
    .

  10. #10
    Membre régulier
    Profil pro
    Inscrit en
    Avril 2007
    Messages
    113
    Détails du profil
    Informations personnelles :
    Localisation : France, Sarthe (Pays de la Loire)

    Informations forums :
    Inscription : Avril 2007
    Messages : 113
    Points : 99
    Points
    99
    Par défaut
    Citation Envoyé par ram-0000 Voir le message
    Toi tu ne fait pas de new mais peut être qu'insidieusement, il y a des new qui sont faits ailleurs dans le code (un vector ou une list qui grandit).
    J'ai vérifiés tous mes vecteurs, aucun ne grandit sans raison. un vecteur ne fait pas de new sans rien dire par contre il alloue de la mémoire que le vecteur conserve tant qu'il existe. et j'ai déjà vérifier mes vecteurs

    Citation Envoyé par ram-0000 Voir le message
    Ce que tu peux faire si tu maitrise le code de l'application c'est de surcharger le new et le delete global...
    c'est pas les new

    Citation Envoyé par ram-0000 Voir le message
    Je ne sais pas si Valgrind ne sait pas faire de la détection de fuite mémoire.
    Je vais regarder valgrind...pour voir

  11. #11
    Alp
    Alp est déconnecté
    Expert éminent sénior

    Avatar de Alp
    Homme Profil pro
    Inscrit en
    Juin 2005
    Messages
    8 575
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 35
    Localisation : France, Bouches du Rhône (Provence Alpes Côte d'Azur)

    Informations forums :
    Inscription : Juin 2005
    Messages : 8 575
    Points : 11 860
    Points
    11 860
    Par défaut
    Pour plus de "sécurité" sur l'allocation dynamique, essaye les pointeurs intelligents. Ce sera standard dans la prochaine version de C++ via les Smart Pointers de Boost, donc Loïc parle dans son article. Ca t'assurera l'absence de problèmes de ce côté là et te permettra de trouver la vraie source.

  12. #12
    Membre éprouvé
    Profil pro
    Inscrit en
    Mai 2006
    Messages
    780
    Détails du profil
    Informations personnelles :
    Localisation : France, Haute Garonne (Midi Pyrénées)

    Informations forums :
    Inscription : Mai 2006
    Messages : 780
    Points : 1 176
    Points
    1 176
    Par défaut
    ben si toi même qui a fait l'appli tu sais pas quelle partie serait susceptible de faire monter la mémoire, on va pas pouvoir t'aider beaucoup plus

    sinon oui si en supprimant certaines parties/faire du debug tu n'arrives à rien voir, utilise quelque chose comme valgrind

  13. #13
    Membre régulier
    Profil pro
    Inscrit en
    Avril 2007
    Messages
    113
    Détails du profil
    Informations personnelles :
    Localisation : France, Sarthe (Pays de la Loire)

    Informations forums :
    Inscription : Avril 2007
    Messages : 113
    Points : 99
    Points
    99
    Par défaut
    Citation Envoyé par nikko34 Voir le message
    ben si toi même qui a fait l'appli tu sais pas quelle partie serait susceptible de faire monter la mémoire, on va pas pouvoir t'aider beaucoup plus
    Oui je sais

    en ce moment j'utilise le gestionnaire de mémoire de windows il me dis dans l'onglet processus combien mon appli prend de mémoire... et en faisant du pas a pas ca me permet de voir ce qui pose pb.

    sauf que ce gestionnaire ne me donne qu'une valeur arrondie... je trouve ce soir ou je me pends a ma souris.
    ->je télécharge process explorer :p (mais finalement ca me donne pas la taille memoire a l'octet pret....)

  14. #14
    Rédacteur/Modérateur
    Avatar de JolyLoic
    Homme Profil pro
    Développeur informatique
    Inscrit en
    Août 2004
    Messages
    5 463
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 49
    Localisation : France, Yvelines (Île de France)

    Informations professionnelles :
    Activité : Développeur informatique
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Août 2004
    Messages : 5 463
    Points : 16 213
    Points
    16 213
    Par défaut
    Une technique qui peut aider :
    Met un compteur d'instance avec trace dans les principaux objets de ton application, et regarde si le nombre d'un de ces objets augmente insidieusement. Ça peut déjà aider à cibler le problème.

    Par exemple, un truc genre :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    31
    32
    template <class T> struct InstanceCounter
    {
    	InstanceCounter(std::string const &name) : myName(name)
    	{
    		++count;
    		display("(++)");
    	}
    	~InstanceCounter() 
    	{
    		--count;
    		display("(--)");
    	}
    	void display(std::string const &reason)
    	{
    		cout << "Number of " << myName << ": " << count << reason << endl
    	}
    	static int count;
    	std::string myName;
    };
     
    class MaClasseATester 
    #ifndef NDEBUG
        : InstanceCounter<MaClasseATester>
    #endif
    {
        MaClasseATester() 
    #ifndef NDEBUG
             : InstanceCounter<MaClasseATester> ("MaClasseATester (default cstr)")
    #endif
        {}
      // ...
    };
    Ma session aux Microsoft TechDays 2013 : Développer en natif avec C++11.
    Celle des Microsoft TechDays 2014 : Bonnes pratiques pour apprivoiser le C++11 avec Visual C++
    Et celle des Microsoft TechDays 2015 : Visual C++ 2015 : voyage à la découverte d'un nouveau monde
    Je donne des formations au C++ en entreprise, n'hésitez pas à me contacter.

  15. #15
    Membre régulier
    Profil pro
    Inscrit en
    Avril 2007
    Messages
    113
    Détails du profil
    Informations personnelles :
    Localisation : France, Sarthe (Pays de la Loire)

    Informations forums :
    Inscription : Avril 2007
    Messages : 113
    Points : 99
    Points
    99
    Par défaut
    Citation Envoyé par JolyLoic Voir le message
    Une technique qui peut aider :
    Met un compteur d'instance avec trace dans les principaux objets de ton application, et regarde si le nombre d'un de ces objets augmente insidieusement. Ça peut déjà aider à cibler le problème.
    Merci, ça peut servir carrément, mais je rappelle que ce n'est pas un probleme de new : j'ais crée TOUS mes objets au départ, je les stocke dans un vecteur et quand j'en ai besoin, au lieu de faire un new je vais piocher dedans et au lieu de faire un delete je les replace dans le vecteur.
    ->pas de new dans mon programme, donc le compteur d'instance ne m'aidera pas :p

    j'ai résolu le pb, j'avais des informations de debug sous la forme de string concaténé (je sais c'est mal) plus le temps passait plus mes objets stockaient des informations dans ce string. En virant ce string de debug ca marche mieux.

    merci de votre réactivité, merci a ceux qui m'ont aidé :p ca fait du bien de ne pas se sentir seul

    Vincent, j'ai plus de fuite, ça monte ça descend, ça doit être due a des taches solaires.

  16. #16
    Rédacteur/Modérateur
    Avatar de JolyLoic
    Homme Profil pro
    Développeur informatique
    Inscrit en
    Août 2004
    Messages
    5 463
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 49
    Localisation : France, Yvelines (Île de France)

    Informations professionnelles :
    Activité : Développeur informatique
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Août 2004
    Messages : 5 463
    Points : 16 213
    Points
    16 213
    Par défaut
    Citation Envoyé par Fraggy Voir le message
    Merci, ça peut servir carrément, mais je rappelle que ce n'est pas un probleme de new : j'ais crée TOUS mes objets au départ
    Il y a une différence entre ne pas avoir de new, et ne pas créer d'objets... Mais puisque tu as résolu ton problème, c'est que c'était autre chose...
    Ma session aux Microsoft TechDays 2013 : Développer en natif avec C++11.
    Celle des Microsoft TechDays 2014 : Bonnes pratiques pour apprivoiser le C++11 avec Visual C++
    Et celle des Microsoft TechDays 2015 : Visual C++ 2015 : voyage à la découverte d'un nouveau monde
    Je donne des formations au C++ en entreprise, n'hésitez pas à me contacter.

  17. #17
    Expert confirmé
    Homme Profil pro
    Ingénieur développement logiciels
    Inscrit en
    Décembre 2003
    Messages
    3 549
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Essonne (Île de France)

    Informations professionnelles :
    Activité : Ingénieur développement logiciels

    Informations forums :
    Inscription : Décembre 2003
    Messages : 3 549
    Points : 4 625
    Points
    4 625
    Par défaut
    Valgrind est le meilleur outil pour ça.
    Il te permettra de tout vérifier, erreurs mémoires, fuites, etc. dans l'intégralité du programme.
    Boost ftw

  18. #18
    Membre régulier
    Profil pro
    Inscrit en
    Avril 2007
    Messages
    113
    Détails du profil
    Informations personnelles :
    Localisation : France, Sarthe (Pays de la Loire)

    Informations forums :
    Inscription : Avril 2007
    Messages : 113
    Points : 99
    Points
    99
    Par défaut
    Il y a une différence entre ne pas avoir de new, et ne pas créer d'objets...
    Comment on fait (sans faire de new ou de malloc) pour créer un objet qui restera en mémoire même si on quitte la fonction qui vient de le créer ?

    J'avais pensé à un vecteur qui grandissaient (alors qu'il ne devait pas) et finalement c'était un string (j'avais des milliers de spheres dans mon vecteur et chaque sphere dispose d'un string de debug qui enregistrait tout ce qui se passaient scrupuleusement...)

    Vincent

  19. #19
    Rédacteur/Modérateur
    Avatar de JolyLoic
    Homme Profil pro
    Développeur informatique
    Inscrit en
    Août 2004
    Messages
    5 463
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 49
    Localisation : France, Yvelines (Île de France)

    Informations professionnelles :
    Activité : Développeur informatique
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Août 2004
    Messages : 5 463
    Points : 16 213
    Points
    16 213
    Par défaut
    Citation Envoyé par Fraggy Voir le message
    Comment on fait (sans faire de new ou de malloc) pour créer un objet qui restera en mémoire même si on quitte la fonction qui vient de le créer ?

    J'avais pensé à un vecteur qui grandissaient
    Justement, on fait avec un tel vecteur, dans lequel on colle l'objet qu'on vient de créer.
    Ma session aux Microsoft TechDays 2013 : Développer en natif avec C++11.
    Celle des Microsoft TechDays 2014 : Bonnes pratiques pour apprivoiser le C++11 avec Visual C++
    Et celle des Microsoft TechDays 2015 : Visual C++ 2015 : voyage à la découverte d'un nouveau monde
    Je donne des formations au C++ en entreprise, n'hésitez pas à me contacter.

+ Répondre à la discussion
Cette discussion est résolue.

Discussions similaires

  1. Une fuite de mémoire ?
    Par 304bl dans le forum Général Java
    Réponses: 8
    Dernier message: 30/03/2013, 08h28
  2. Réponses: 7
    Dernier message: 20/12/2009, 18h42
  3. Réponses: 2
    Dernier message: 26/10/2005, 11h44
  4. Réponses: 12
    Dernier message: 14/07/2005, 16h55
  5. Réponses: 9
    Dernier message: 31/05/2005, 10h05

Partager

Partager
  • Envoyer la discussion sur Viadeo
  • Envoyer la discussion sur Twitter
  • Envoyer la discussion sur Google
  • Envoyer la discussion sur Facebook
  • Envoyer la discussion sur Digg
  • Envoyer la discussion sur Delicious
  • Envoyer la discussion sur MySpace
  • Envoyer la discussion sur Yahoo