Skip to content

Comment obtenir l’adresse relative d’un champ dans un dump de structure. [C]

Solution:

Tu peux le faire avec gdb. A titre d’exemple, je vais utiliser cette source:

struct A {
  int a;
  char b;
  short c;
};

int main() {
  struct A a;
}

Chargement du binaire dans gdb:

(gdb) print (int)&((struct A*)0)->a
$1 = 0
(gdb) print (int)&((struct A*)0)->b
$2 = 4
(gdb) print (int)&((struct A*)0)->c
$3 = 6

METTRE À JOUR:

Si vous devez le faire pour un grand nombre de champs, vous trouverez peut-être pratique d’utiliser la nouvelle interface python de GDB (vous aurez besoin d’une version récente de GDB pour l’utiliser, j’utilise 7.4). J’ai créé offsets.py :

import gdb

class Offsets(gdb.Command):
    def __init__(self):
        super (Offsets, self).__init__ ('offsets-of', gdb.COMMAND_DATA)

    def invoke(self, arg, from_tty):
        argv = gdb.string_to_argv(arg)
        if len(argv) != 1:
            raise gdb.GdbError('offsets-of takes exactly 1 argument.')

        stype = gdb.lookup_type(argv[0])

        print argv[0], '{'
        for field in stype.fields():
            print '    %s => %d' % (field.name, field.bitpos//8)
        print '}'

Offsets()

Ensuite, vous pouvez ajouter à votre .gdbinit :

python
sys.path.insert(0, '/path/to/script/dir')
import offsets
end

Ensuite, en l’utilisant dans GDB, comme :

(gdb) offsets-of "struct A"
struct A {
    a => 0
    b => 4
    c => 6
}

Ce script fait quelques hypothèses simplificatrices, comme le fait que vous n’utilisez pas de champs de bits, et qu’il ne creuse pas dans les structures imbriquées, mais ces modifications sont3 assez simples si vous en avez besoin.

Vous pouvez le faire à partir d’un programme C en utilisant le standard offsetof() macro, définie dans stddef.h. Cependant, je ne suis pas sûr que ce soit ce que vous voulez, car vous ne pourrez peut-être pas l’exécuter (le compiler sur l’hôte renverra probablement des décalages erronés).

#include <stdio.h>
#include <stddef.h>

struct A {
  int a;
  char b;
  short c;
};

int main() {
    printf("Offset of b in A is %zun", offsetof(struct A, b));
    return 0;
}

Cependant, vous pourrez peut-être utiliser quelques hacks pour obtenir le décalage d’un binaire compilé sans l’exécuter. Peut-être attribuer à une variable statique la valeur de décalage et trouver un moyen d’obtenir sa valeur.



Articles Similaires

Laisser un commentaire

Votre adresse e-mail ne sera pas publiée.