logo Debian Debian Debian-France Debian-Facile Debian-fr.org Forum-Debian.fr Debian ? Communautés logo inclusivité

Debian-facile

Bienvenue sur Debian-Facile, site d'aide pour les nouveaux utilisateurs de Debian.

Vous n'êtes pas identifié(e).

#1 20-10-2018 18:18:21

Anonymous
Membre
Distrib. : Devuan 2.0
Noyau : Linux 4.9.0-8-amd64
(G)UI : XFCE
Inscription : 28-11-2017

C/C++ compilation en statique et utilisation mémoire.

Bonjour à tous,

J'ai fait un test de compilation en statique, avec l'option -static de gcc.

Et voici la comparaison de la taille des deux programmes:
- 14 ko en dynamique
- 1500 ko en static

Mais voilà, quand je lance le programme, le gestionnaire de tâches de LXDE me dit qu'en mémoire leur taille est la suivante:
- 1000 ko en dynamique
- 4 ko en static

Quand je lance la commande "ps" dans un terminal, elle me donne les mêmes valeurs.


Donc si quelqu'un peut m'expliquer pourquoi un fichier de 1500 ko ne prend que 4ko en mémoire ?

Hors ligne

#2 20-10-2018 22:05:43

raleur
Membre
Inscription : 03-10-2014

Re : C/C++ compilation en statique et utilisation mémoire.

Tu parles de la RSS ?

Il vaut mieux montrer que raconter.

Hors ligne

#3 21-10-2018 06:17:49

Anonymous
Membre
Distrib. : Devuan 2.0
Noyau : Linux 4.9.0-8-amd64
(G)UI : XFCE
Inscription : 28-11-2017

Re : C/C++ compilation en statique et utilisation mémoire.

Oui, je suppose que c'est la taille réelle en mémoire, car la VSZ des programmes est énorme.

EDIT: J'ai aussi remarqué qu'à la fin du programme, après avoir exécuté les fonctions de nettoyage et de déconnexion, juste avant la fonction "return", la taille RSS du programme compilé en statique est de 1348 ko.

Donc je trouve ça plutôt étrange que l'exécution de seulement quelques fonctions fasse passer la taille en mémoire de 4 ko à 1348 ko.

Voici le code de fin de programme:

  endthread = 1;
  void * ret;
  pthread_join(tid,&ret);

  // ordonne au serveur X de se détacher de la mémoire partagée:
  xcb_shm_detach(c, info.shmseg);

  // Détachement local du segment de mémoire partagée:
  shmdt(info.shmaddr);

  // ordonne au serveur X de libérer la mémoire allouée au pixmap:
  xcb_free_pixmap(c, pix);

  // ordonne au serveur X de détruire la fenêtre, et déconnexion:
  xcb_destroy_window(c, win);
  xcb_disconnect(c);
 
  // nanosleep pour avoir le temps de regarder la mémoire
  // consommée par le processus:
  slp.tv_sec = 10;
  slp.tv_nsec = 500000000L;
  clock_nanosleep(CLOCK_REALTIME,0,&slp,NULL);

  return 0;



En supposant que ce code ne soit pas chargé en mémoire au début du programme, 1348 ko ça me parait beaucoup pour si peu de code.

Dernière modification par Anonymous (21-10-2018 10:15:33)

Hors ligne

#4 21-10-2018 11:37:31

kao
Modérateur
Distrib. : Testing
Noyau : Linux 4.quelquechose
(G)UI : Gnome 3
Inscription : 27-09-2012
Site Web

Re : C/C++ compilation en statique et utilisation mémoire.

Attention à ne pas confondre taille du programme sur le disque et la taille prise en Ram.
Je peux avoir une image dans mon programme et en charger 1000 copies dans la Ram.
Tous dépends de l'utilisation que l'on en fait.
On peut aussi oublier de libérer les mémoires allouées précédemment avec un malloc ou un new. C'est une des façons de fabriquer de la fuite de mémoire.
On ne le voit pas toujours parce que l'OS force la libération de la mémoire à la fermeture du programme même si on ne l'a pas fait proprement dans son code.

On peut tracer les fuites de mémoires avec Valgrind :

valgrind --leak-check=yes --log-file=valgrind.log ./bin/monprog
valgrind --leak-check=full --show-leak-kinds=all --log-file=valgrind.log ./bin/monprog



Le log valgrind.log n'est pas toujours facile à lire mais il y a des aides pour ça :
https://connect.ed-diamond.com/GNU-Linu … c-Valgrind
http://sdz.tdct.org/sdz/debuguer-facile … grind.html

Il faut l'option -g dans gcc pour le debug avec Valgrind je crois

J'utilise aussi linux-perf pour voir dans quoi le programme passe le plus de temps :

apt install linux-perf
perf record -g ./build/kingsandships -sleep 10


perf report --sort comm,dso

Hors ligne

#5 21-10-2018 12:21:34

raleur
Membre
Inscription : 03-10-2014

Re : C/C++ compilation en statique et utilisation mémoire.

Anonymous a écrit :

Donc je trouve ça plutôt étrange que l'exécution de seulement quelques fonctions fasse passer la taille en mémoire de 4 ko à 1348 ko.


Moi, je trouve étrange qu'un exécutable actif occupe seulement 4 Kio en mémoire, soit la taille d'une page. Il me semble que normalement il devrait y avoir au minimum une page pour le code et une page pour les données et la pile.


Il vaut mieux montrer que raconter.

Hors ligne

#6 22-10-2018 16:45:28

Anonymous
Membre
Distrib. : Devuan 2.0
Noyau : Linux 4.9.0-8-amd64
(G)UI : XFCE
Inscription : 28-11-2017

Re : C/C++ compilation en statique et utilisation mémoire.

Merci kao pour tes conseils, ça me sera très utile, car je compte faire un programme qui utilise le moins de mémoire possible et le plus performant possible.

Hors ligne

#7 30-10-2018 09:23:29

kao
Modérateur
Distrib. : Testing
Noyau : Linux 4.quelquechose
(G)UI : Gnome 3
Inscription : 27-09-2012
Site Web

Re : C/C++ compilation en statique et utilisation mémoire.

Attention moins de chose en mémoire peuvent dire plus d'accés disque....ou plus de temps de calcul.
C'est un compromis à trouver.
Par exemple il vaut parfois mieux charger une image en ram une fois au démarrage plutôt qu'a chaque fois que l'on veut l'afficher... Cela prends de la ram tout le temps mais évite de nombreux accés disques.
On peut aussi répéter un calcul x fois alors que les valeurs d'entrées n'ont pas changé. Il vaut mieux stocker le résultat et regarder si les valeurs d'entrée ont changé avant de refaire le calcul.
J'utilise le SDL2, et pour afficher du texte il faut d'abord la convertir en texture (ce qui demande du calcul) avant de l'afficher.
Comme j'affiche le texte 30 fois par seconde je préfére stocker la texture et vérifier s'elle n'existe pas déjà avant de la regénérer:

void C_MenuItem::renderText(){
         C_TextureList& t=C_TextureList::Instances(); //singleton dans lequel je stocke toutes mes textures
    if(m_text !=""){ //je vérifie que le texte n'est pas vide
        if(t.searchTexture(m_textName)== nullptr || m_text != m_oldText){ //je vérifie que la texture n'existe pas déjà ou que le texte a changé depuis la dernière fois
                t.loadTextAsTexturesIntoMap(m_textName, m_text, m_fontSize, m_color); // si ça remplie les conditions, je génére la nouvelle texture et la stocke dans mon singleton
                m_oldText = m_text; //je garde en mémoire le nouveau texte pour la prochaine fois
            }
        t.renderTexture(m_textName, m_x_screen + m_width/2, m_y_screen +  m_height/2,CENTER); //j'affiche le texte
        }
}
 


Comme c'est une histoire de compromis et tout dépends de ce que tu veux faire,  je te conseille de compter le nombre de fois qu'une fonction gourmande en ressource est utilisée.
Perso pendant le dévelloppement je place un compteur que j'enléverai ensuite juste pour voir.


int count = 0;
function(){
count++;
}
cout << "total : "<< count << end;
 


Il y a peut-être plus malin, mais cela m'a permis de voir que certaines fois je sur-utilisais une fontion et qu'elle n'était pas obligatoirement bien placé dans mon programme.
En espérant que cela puisse aider...

Hors ligne

Pied de page des forums