GDB: Как напечатать значение по адресу памяти в ASM
0x08048c62 <+0>: sub $0x2c,%esp
0x08048c65 <+3>: lea 0x1c(%esp),%eax
0x08048c69 <+7>: mov %eax,0xc(%esp)
0x08048c6d <+11>: lea 0x18(%esp),%eax
0x08048c71 <+15>: mov %eax,0x8(%esp)
0x08048c75 <+19>: movl $0x804a73d,0x4(%esp)
0x08048c7d <+27>: mov 0x30(%esp),%eax
0x08048c81 <+31>: mov %eax,(%esp)
0x08048c84 <+34>: call 0x80488d0 <__isoc99_sscanf@plt>
=> 0x08048c89 <+39>: cmp $0x1,%eax
Как распечатать то, что в $0x1
в последней инструкции? Я перепробовал все комбинации
x/d 0x1
x/d $0x1
x/s $0x1
...
...
Но я либо получаю сообщение об ошибке: не удается получить доступ к памяти по адресу 0x1, либо значение не может быть преобразовано в целое число (даже если я пытаюсь изменить тип на c,s,x,a)
В конечном счете, я пытаюсь выяснить аргументы, переданные scanf
"%d %d %c"
1 ответ
$1
есть непосредственное значение, это просто число 1
, Это не адрес. Это проверяет возвращаемое значение sscanf
, то есть количество обработанных элементов. Преобразованные значения, конечно, помещаются в память по указателям, которые были переданы sscanf
в качестве аргументов.
В вашем примере строка формата 0x804a73d
, вы должны быть в состоянии распечатать, используя x/s 0x804a73d
,
Код использует mov
положить предметы в стек вместо push
по соображениям эффективности. Вы можете видеть аргументы в правильных смещениях в стеке. Они начинаются в (%esp)
и каждый составляет 4 байта:
1-й аргумент (строка для чтения):
0x08048c7d <+27>: mov 0x30(%esp),%eax
0x08048c81 <+31>: mov %eax,(%esp)
2-й аргумент (строка формата):
0x08048c75 <+19>: movl $0x804a73d,0x4(%esp)
3-й аргумент (1-й выходной указатель):
0x08048c6d <+11>: lea 0x18(%esp),%eax
0x08048c71 <+15>: mov %eax,0x8(%esp)
4-й аргумент (2-й выходной указатель):
0x08048c65 <+3>: lea 0x1c(%esp),%eax
0x08048c69 <+7>: mov %eax,0xc(%esp)