Re: Linux supporte-t-il les fichiers creux ?

Page principale

Répondre à ce message
Auteur: Xavier Bestel
Date:  
À: guilde
Sujet: Re: Linux supporte-t-il les fichiers creux ?
Le mar 06/01/2004 à 17:07, Yves Martin a écrit :
> C'est étrange - un objdump -h core me retourne des sections markées 'code'
> Peut-être qu'il y a eu des améliorations depuis le noyau 2.4 pour ne pas
> inclure les sections text read-only mais laisser gdb les récupérer de
> l'exécutable (ou .so) d'origine.


Oui, alors selon le code du 2.6, les sections de code font partie des
VMA à ne pas dumper. Cependant, les VMA non dumpées ont quand même un
header, mais avec une taille de zéro:

(ligne 1352 de binfmt_elf.c du 2.6.0)

        sz = vma->vm_end - vma->vm_start;


        phdr.p_type = PT_LOAD;
        phdr.p_offset = offset;
        phdr.p_vaddr = vma->vm_start;
        phdr.p_paddr = 0;
        phdr.p_filesz = maydump(vma) ? sz : 0;   <= c'est ici !!!
        phdr.p_memsz = sz;


(la fonction maydump() est celle qui fait le tri de ce qui est dumpable
ou pas, suivant le type de la VMA)
J'imagine que les VMA code ne sont pas incluses car gdb se débrouille
très bien à partir de l'exécutable et des libraries.

Si maintenant on regarde en détail notre fichier core du "crash"
d'Edgar:

[xav@bip:~]$ objdump -h core

core:     format de fichier elf32-i386


Sections:
Idx Nom           Taille    VMA       LMA       Fich off  Algn
  0 note0         000007dc  00000000  00000000  000000b4  2**0
                  CONTENTS, READONLY
  1 .reg/12918    00000044  00000000  00000000  0000010c  2**2
                  CONTENTS
  2 .reg          00000044  00000000  00000000  0000010c  2**2
                  CONTENTS
  3 load1         00000000  08048000  00000000  00001000  2**12
                  CONTENTS, ALLOC, LOAD, READONLY, CODE
  4 load2         00001000  08049000  00000000  00001000  2**12
                  CONTENTS, ALLOC, LOAD
  5 load3         00001000  bffff000  00000000  00002000  2**12
                  CONTENTS, ALLOC, LOAD, CODE


Les sections qui nous intéressent sont load1, 2 et 3.

load1: commence à 0x08048000, ça doit donc être le code du programme. On
voit effectivement que la taille fait 0, donc la VMA correspondante
n'est pas dans le fichier, il s'agit juste d'une indication.

load2: vient juste après, n'est pas exécutable (pas marquée "CODE"), ça
doit être la section .data ou .bss (data non initialisée) de notre
programme. Taille: 4k, soit une page.

load3: intéressant, une VMA d'1 page (4k) marquée "CODE" ? en fait, à
cette adresse (0xbffff000) il s'agit de la pile. Eh oui, la pile est
exécutable ! C'est d'ailleurs la source de bien des trous de sécurité,
et c'est pourquoi il existe des patches pour linux qui marquent cette
pile comme non-exécutable.




On va jeter un oeil à la carte mémoire de l'exécutable* de départ pour
confirmer:

[xav@bip:~]$ pmap `pidof crash`
13001:   ./crash
08048000      4K read/exec         /home/xav/crash
08049000      4K read/write        /home/xav/crash
bffff000      4K read/write/exec     [ anon ]
 total       12K



Effectivement, une VMA code, suivie d'une VMA data (bss en fait, pour
les curieux objdump -h crash), et beaucoup plus loin, la pile.
Seules les 2 dernières sections sont intéressantes pour gdb.

Cet exemple est simple puisqu'Edgar a volontairement omis toutes les
bibliothèques partagées avec lesquelles on fait normalement un
exécutable, mais en pratique il y a juste beaucoup plus de VMA.

> Je cherchais de la doc sur le format core ou plutôt comment le dump
> est stocké au format ELF - que je n'ai pas encore trouvée
> - mais je n'aurais jamais imaginé regardé dans les sources sur kernel...


C'est bien la particularité des logiciels libres: pas toujours de doc à
jour, mais le source est là en cas de doute.

    Xav


* j'ai un peu triché pour que "crash" s'arrête au lieu de planter, sinon
c'est tout pareil.