Comment démonter une plage de mémoire avec GDB?

J’essaie de démonter un programme pour voir une instruction d’assembly syscall (l’instruction INT, je crois) et le gestionnaire avec GDB et j’ai écrit un petit programme (voir ci-dessous) qui ouvre et ferme un fichier.

J’ai été en mesure de suivre l’appel pour créer avec GDB jusqu’à ce qu’il exécute un appel.

Lorsque j’ai essayé de dire à GDB “désassembler 0x ….” (adresse d’appel), il a répondu avec “Aucune fonction contient l’adresse spécifiée”.

Est-il possible de forcer GDB à désassembler (ou à l’afficher dans l’assembleur le mieux possible) cette adresse mémoire? Si c’est le cas, comment?

#include  #include  int main() { FILE* f; f = fopen("main.c", "r"); if (!f) { perror("open"); return -1; } fclose(f); return 0; } 

Voulez-vous seulement démonter votre main principale? Si oui, essayez ceci:

 (gdb) info line main (gdb) disas STARTADDRESS ENDADDRESS 

Ainsi:

 USER@MACHINE /cygdrive/c/prog/dsa $ gcc-3.exe -g main.c USER@MACHINE /cygdrive/c/prog/dsa $ gdb a.exe GNU gdb 6.8.0.20080328-cvs (cygwin-special) ... (gdb) info line main Line 3 of "main.c" starts at address 0x401050 
and ends at 0x401075 : push %ebp 0x00401051 : mov %esp,%ebp 0x00401053 : sub $0x18,%esp 0x00401056 : and $0xfffffff0,%esp 0x00401059 : mov $0x0,%eax 0x0040105e : add $0xf,%eax 0x00401061 : add $0xf,%eax 0x00401064 : shr $0x4,%eax 0x00401067 : shl $0x4,%eax 0x0040106a : mov %eax,-0xc(%ebp) 0x0040106d : mov -0xc(%ebp),%eax 0x00401070 : call 0x4010c4 <_alloca> End of assembler dump.

Je ne vois pas votre appel d’interruption du système cependant. (ça fait longtemps que je n’ai pas essayé d’appeler le système en assemblée. INT 21h cependant, dernier rappel

Ouais, le déassembly n’est pas la meilleure commande à utiliser ici. La commande que vous voulez est “x / i” (examinez comme instructions):

 (gdb) x/i 0xdeadbeef 

Ce n’est pas la réponse directe à votre question, mais comme vous semblez vouloir simplement démonter le binary, vous pouvez peut-être utiliser objdump :

 objdump -d program 

Cela devrait vous donner son déassembly. Vous pouvez append -S si vous souhaitez qu’il soit annoté à la source.

fopen () est une fonction de bibliothèque C et, par conséquent, vous ne verrez aucune instruction syscall dans votre code, juste un appel de fonction normal. À un moment donné, il appelle ouvert (2), mais cela se fait via un trampoline. Il y a simplement un saut vers la page VDSO, fournie par le kernel à chaque processus. Le VDSO fournit alors le code pour effectuer l’appel système. Sur les processeurs modernes, les instructions SYSCALL ou SYSENTER seront utilisées, mais vous pouvez également utiliser INT 80h sur les processeurs x86.

Vous pouvez forcer gcc à sortir directement en code assembleur en ajoutant le commutateur -S

 gcc -S hello.c 

Si tout ce que vous voulez est de voir le désassemblage avec l’appel INTC, utilisez objdump -d comme quelqu’un l’a mentionné, mais utilisez l’option -static lors de la compilation. Sinon, la fonction fopen n’est pas compilée dans elf et est liée à l’exécution.

Vous n’avez pas besoin d’utiliser gdb. GCC le fera.

  gcc -S foo.c 

Cela créera des objects qui sont l’assemblage.

 gcc -m32 -c -g -Wa,-a,-ad foo.c > foo.lst 

La version ci-dessus créera un fichier de liste contenant à la fois le C et l’assembly généré. FAQ GCC

gdb disassemble a un / m pour inclure le code source aux côtés des instructions. Ceci est équivalent à objdump -S, avec l’avantage supplémentaire de se limiter à une seule fonction (ou plage d’adresses) d’intérêt.