Добавил:
Upload Опубликованный материал нарушает ваши авторские права? Сообщите нам.
Вуз: Предмет: Файл:
ida.final.doc
Скачиваний:
0
Добавлен:
01.05.2025
Размер:
6 Mб
Скачать

Long GetReg (long ea,char reg);

Возвращает значение сегментных регистров в произвольной точке программы. Подробнее об этом можно прочитать в описании функции SetReg.

операнд

Пояснения

‘ea’

линейный адрес, в котором необходимо определить значение регистра

‘reg’

символьное имя регистра. Например “DS”, “GS” и так далее

Return

==return

Пояснения

!=0xFFFF

Значение сегментного регистра в параграфах

==0xFFFF

Ошибка

Функция возвращает 16-битное целое, содержащие значение сегментного регистра в параграфах. В 32-битных программах функция обычно возвращает не непосредственное значение, а селектор.

Для получения искомого адреса необходимо воспользоваться функцией AskSelector. Поскольку селекторы «визуально» неотличимы от адресов сегментов, то для уверенности необходимо вызывать AskSelector всякий раз для проверки на принадлежность возвращаемого значения к селекторам. Если селектор с указанным номером не существует, то это непосредственное значение.

Если регистр не существует (например “MS”) или не определен, то функция и в том и другом случае вернет ошибку 0xFFFF, а не BADADDR, как утверждает прилагаемая к IDA документация.

Пример использования:

seg000:0000 seg000 segment byte public 'CODE' use16

seg000:0000 assume cs:seg000

Message (“%x \n”,

GetReg (0x10000,”CS”)

);

1000

.text:00401000 _text segment para public 'CODE' use32

.text:00401000 assume cs:_text

Message (“%x \n”,

GetReg (ScreenEA (),”CS”)

);

1

Message (“%x \n”,

AskSelector (1)

);

0

Перекрестные ссылки что такое перекрестные ссылки?

Долгое время SOURCER лидировал среди других дизассемблеров в умении находить и восстанавливать перекрестные ссылки. На этом, правда, его основные достоинства и оканчивались, но все равно он активно использовался для исследования программного обеспечения.

Что же такое перекрестные ссылки и почему они так важны для популярности дизассемблера? Покажем это на следующем примере. Рассмотрим простейший случай. Допустим, исходный файл выглядел так:

.MODEL TINY

.CODE

ORG 100h

Start:

MOV AH,9

LEA DX,s0

INT 21h

RET

s0 DB "Hello, Sailor!",0Dh,0Ah,'$'

END Start

После ассемблирования он будет выглядеть следующим образом:

seg000:0100 start proc near

seg000:0100 mov ah, 9

seg000:0102 mov dx, offset aHelloSailor ; "Hello, Sailor!\r\n$"

seg000:0105 int 21h

seg000:0105

seg000:0107 retn

seg000:0107 start endp

seg000:0107

seg000:0107 ; ---------------------------------------------------------------------------

seg000:0108 aHelloSailor db 'Hello, Sailor!',0Dh,0Ah,'$'

seg000:0108 seg000 ends

Допустим, мы хотим узнать, какой код выводит эту строку на экран. Когда-то для этого приходилось кропотливо изучать весь листинг, и то не было шансов, что с первого раза выводящий строку код удастся рассмотреть.

Поэтому, эту задачу возложили на плечи дизассемблера. Так, что бы машина сама анализировала выполнение программы и восстанавливала все связи. Это невероятно упростило анализ программ, как впрочем, и взлом защит.

Стало достаточно только найти в строку, которая защита выводит в случае неудачного завершения проверки (ключевой дискеты ли, или пароля – совершенно не важно), как дизассемблер поможет мгновенно найти, вводящий ее код, а значит, и локализовать защиту каким бы длинной программа не оказалась.

Как правило, где-то неподалеку расположен условный переход, передающий управление этой ветви. Стоит только изменить его на противоположный, как защиту можно считать взломанной.

Но ведь же не для хакерства же были придуманы перекрестные ссылки! Разумеется, нет! Помощь хакерам это только побочный эффект (хотя и очень приятный для них). Значительно важнее поддержка перекрестных ссылок чтобы правильно дизассемблировать код!

Покажем это на следующем примере:

.MODEL TINY

.CODE

ORG 100h

Start:

LEA AX,s0

PUSH AX

CALL Print

RET

s0 DB 'Hello, Sailor!',0Dh,0Ah,'$'

Print:

POP AX

POP DX

PUSH AX

MOV AH,9

INT 21h

RET

END Start

Первые четыре строки любой дизассемблер разберет без труда. Но вот дальше начнутся сложности. Как узнать, что следом идет текстовая строка, а не исполняемый код? Если же дизассемблировать как код из соображений одной лишь надежды на это, то полуученый результат станет похожим на бред и вся программа окажется дизассемблированной неправильно.

Поэтому приходится эмулировать ее исполнение и отслеживать все косвенные и непосредственные переходы. Если ассемблер сумеет распознать вызов подпрограммы, то ссылку на строку он восстановит с куда большей легкостью.

Однако, тут скрывается один подводный камень. Эмуляция (даже частичная) требует больших накладных расходов, и если каждый раз ее выполнять «налету», то никаких вычислительных ресурсов не хватит для нормальной работы!

Поэтому приходится прибегать к компиляции. Да, именно к компиляции. Ведь компиляция это только перевод с одного языка в другой, а не обязательно в машинные коды. В данном случае, как раз запутанный язык ассемблера (а точнее одних лишь ссылок) преобразуется к максимально производительно и компактной форме записи. Или другими словами можно сказать, что перекрестные ссылки – это сохраненный результат работы эмулятора.

Кроме того, если выполнение программы однонаправлено, то есть часто невозможно сказать, выполнение какой инструкции предшествовало текущей, то перекрестные ссылки предоставляют такую возможность!

Можно начать изучение программы с любой точки, свободно двигаясь по ходу ее исполнения как взад, так и вперед. Это, в самом деле, очень удобно. Ведь в большинстве случаев не требуется изучить всю программу целиком, а только один из ее компонентов. Например, тот, что отвечает за взаимодействие с интересующим вас форматом файла. Предположим, что в заголовке находится некая сигнатура, которая проверятся исследуемой программой и находится в дизассемблируемом листинге в «прямом виде».

Тогда можно по перекрестным ссылкам, перейти на процедуру загрузки файла и начать ее изучение. И это не единственный пример. Перекрестные ссыпки активно используются при дизассемблировании программ любой сложности и относятся к незаменимым компонентам дизассемблера.

Однако, как нетрудно догадаться, что гарантировано можно отслеживать только непосредственные ссылки, такие как CALL 0x666, а уже MOV DX,0x777 может быть как смещением, так и константой, а про инструкции типа CALL BX говорить и вовсе не приходится – для вычисления значения регистра BX потребуется весьма не хилый эмулятор процессора.

Поэтому не удивительно, что большинство ассемблеров отслеживало перекрестные ссылки из рук вон плохо. Даже первые версии IDA не были совершенны в этом плане.

То есть поддержка перекрестных ссылок имелась, но их созданием приходилось заниматься человеку (ведь IDA изначально планировалась как интерактивная среда!), а не машине.

Но с течением времени ситуация изменялась и интеллектуальные механизмы IDA улучшались. С версии 3.7 она уже значительно превосходила в этом отношении все остальные существующие в мире ассемблеры, включая SOURCER, и продолжала совершенствоваться!

Соседние файлы в предмете [НЕСОРТИРОВАННОЕ]