0% нашли этот документ полезным (0 голосов)
7 просмотров5 страниц

Mov Ax, (200h) Mov BX, 2 Add Ax, BX: CD /prog C:/prog/ TD

Загружено:

adriaandeboer54
Авторское право
© All Rights Reserved
Мы серьезно относимся к защите прав на контент. Если вы подозреваете, что это ваш контент, заявите об этом здесь.
Доступные форматы
Скачать в формате PDF, TXT или читать онлайн в Scribd
0% нашли этот документ полезным (0 голосов)
7 просмотров5 страниц

Mov Ax, (200h) Mov BX, 2 Add Ax, BX: CD /prog C:/prog/ TD

Загружено:

adriaandeboer54
Авторское право
© All Rights Reserved
Мы серьезно относимся к защите прав на контент. Если вы подозреваете, что это ваш контент, заявите об этом здесь.
Доступные форматы
Скачать в формате PDF, TXT или читать онлайн в Scribd

1

4. Первая программа в отладчике.


4.1. Простая программа.
Предположим, мы хотим изучить работу команды сложения двух целых чи-
сел. Первое слагаемое хранится в слове со смещением 200h (в текущем сегменте
данных) — оно будет загружено в регистр AX, второе слагаемое — число 2 —
будет загружено в регистр BX, сумму требуется разместить в AX. Напишем с
этой целью простую программу, содержащую всего три команды.
mov ax,[200h] ; Поместить в аккумулятор содержимое
; слова по адресу DS:200
mov bx,2 ; Поместить в регистр BX число 2 ( BX = 2)
add ax,bx ; Сложить содержимое AX и BX
; и поместить результат в AX (AX = AX + BX)

Комментарии отделены от текста программы точкой с запятой. Рекоменду-


ется каждую фразу комментария начинать с прописной буквы. Если коммента-
рий продолжается на следующей строке, то продолжение фразы начинается со
строчной буквы. Следует понимать, что на самом деле эти три команды являют-
ся только фрагментом программы на языке ассемблера. Если мы собираемся
использовать транслятор (например, MASM или TASM), то к этим командам
нужно добавить еще ряд директив. Однако для отладчика этих команд доста-
точно. Еще заметим, что вместо последних двух команд можно было написать
одну: add ax,2.

4.2. Вызов отладчика.


Вызовем отладчик. Для этого в Windows XP выполним команду Пуск → Все
программы → Стандартные → Командная строка. В появившемся окне введите
команду перехода в каталог prog, а затем вызовите td. (К сожалению, для наших
следующих упражнений почему-то нельзя запускать Turbo Debugger из-под
оболочки FAR.)
…> cd \prog
C:\prog\>td

4.3. Ассемблирование текста программы.


В отладчике имеется мини-ассемблер. Он переводит мнемонику команд в
их машинные коды.
Находясь в панели кода, начнем ввод команд программы. Нажмем букву m
(первая буква команды mov ax,[200h]). Появляется окно "Enter instruction to
assemble" (введите команду, которую нужно ассемблировать). Завершаем ввод
команды и нажимаем Enter. Встроенный мини-ассемблер немедленно преобра-
зует ее в машинный код. Полученный код подвергается обратной операции —
дисассемблированию (получению мнемонической записи команд по их коду).
Поэтому мы видим не тот текст, который мы ввели mov ax,[200h], а не-
сколько другой: mov ax,[200]. Исчезла буква h, т.к. числа в отладчике —
16-ричные. Позднее мы встретим и более радикальные изменения вводимого
текста. Для ввода следующей команды вызываем команду ассемблирования из
локального меню нажатием Ctrl+A (или Alt+F10/Assemble...). В появляющемся
диалоговом окне мы видим ранее введенную команду mov
ax,[200h].Нажимем клавишу  (ранее введенная команда становится выде-
ленной). Нажимаем клавишу End (выделение снимается). Редактируем команду,
2

чтобы получить mov bx,2. Аналогично набираем add ax,bx. И добавим еще
команду nop (нет операции).
Вы увидите в панели кода
cs:0100►A10002 mov ax,[0200]
cs:0103 BB0200 mov bx,0002
cs:0106 03C3 add ax,bx
cs:0108 90 nop
Черный треугольник показывает команду, адрес которой содержится в
CS:IP, т.е. команду, котрая будет выполнена первой при запуске программы на
выполнение.
Если какая-либо команда будет введена неправильно, отладчик сообщит об
этом. Например, если вы введете команду
mov ax[200] (пропущена запятая),
то последует сообщение: Invalid register combination in address expression (невер-
ная регистровая комбинация в адресном выражении).
Код нашей программы занимает байты с 100-го по 108-й, т.е. девять байтов.
Полученные в результате строки имеют формат:
сегмент:смещение машинный код мнемоника
В кодах команд можно увидеть коды операндов в "перевернутом виде":
Расшифруем код A10002. A1 — код пересылки содержимого ячейки памяти в
аккумулятор, 00 — младший байт и 02 — старший байт операнда-источника.
Аналогично расшифровывается код второй команды. Можно убедиться в том,
что машинные коды имеют разную длину: в нашем примере — 1, 2 и 3 байта.

4.4. Заполнение памяти.


Перед выполнением программы нужно занести в слово памяти, располо-
женное по адресу DS:200, число 1. Можно было добавить это действие в нашу
программу в качестве первой команды (чуть позже мы узнаем, как это сделать),
но мы воспользуемся средствами отладчика.
Нажатием Sift+Tab перейдем в панель данных.
Перейдем на адрес 200: Alt+F10 → Goto. Появится окно с запросом адреса,
на который надо перейти: Enter address to position to. Набираем 200 и нажимаем
Enter. В панели данных отображается содержимое байтов, начиная с адреса
DS:0200.
Мы можем ввести слово 0001 как два байта 1,0 (Alt+F10, Change или
Ctrl+C). А можно ввести именно слово, предварительно отобразив содержимое
панели данных как слова (Alt+F10 → Display as → Word или Ctrl+D,W).
В слово можно ввести отрицательное число, например, –16d (испытайте
это: введите это число по адресу 204). А вот в байт отрицательное число непо-
средственно нельзя. Вернитесь к отображению байтов.
Допустим, нам нужно ввести в байт с адресом 208 (в панели данных) деся-
тичное значение –120. Попытка ввода числа –120d приведет к сообщению Syn-
tax error. Но в TD имеется возможность вычислять выражения. Найдем 16-
ричный эквивалент –120d. Для этого выберем в главном меню Data
→ Evaluate/modify (или нажмем Ctrl+F4). Введем в поле Expression число –120d
и нажмем Enter. В поле Result прочитаем: word –120 (FF88h). Отбрасывая рас-
ширение знакового бита, вводим число 88h.

4.5. Выполнение программы "по шагам".


3

В этом режиме после каждой команды выполнение будет приостанавли-


ваться. Для этого нажимаем клавишу F7в (Trace — трассировка). Выполняется
команда, адрес которой содержится в IP. Выполним первую команду.
Обратите внимание, что изменилось содержимое только двух регистров:
AX — в него загружено значение 1, и IP — в нем адрес следующей выполняе-
мой команды. Флаги не изменились.
Вновь нажмите F7. После выполнения второй команды меняется BX и IP.
Флаги не изменились.
Только после выполнения команды add ax,bx изменилось содержимое
регистра флагов. Правда это коснулось только одного флага PF (в младшем бай-
те результата (03h=00000011b) установлено два бита, то есть четное число би-
тов).

4.6. Выполнение всей программы.


Если нужно вновь прогнать программу по шагам, сначала следует в счетчик
команд занести 0100 — адрес первой команды. Для этого переместитесь в пане-
ли кода на команду с адресом 100: Alt+F10 → Goto и введите 100. Будет выде-
лена команда с адресом 100. А теперь сделаем так, чтобы IP содержал адрес
этой команды: Alt+F10 → New cs:ip. В строке подсказки при выборе этого
пункта меню вы увидите: Set the cs:ip to the current location — установить CS:IP
в текущее положение курсора. Эквивалентная команда — Ctrl+N. Теперь вновь
можно нажимать F7.
Занесите в слово по адресу 200 число –2. Посмотрим, как программа отра-
ботает с такими исходными данными. Выполнить программу как единое целое
можно так: переместим курсор на команду nop в конце программы (только для
этой цели она нам и понадобилась). При этом в IP, разумеется, должен быть
стартовый адрес программы. Нажмем клавишу F4 (Here — здесь). Программа
будет выполнена. Изучите флаги.

4.7. Сохранение файла с программой на диске.


Сохраним код программы. Для этого, нажимая Shift+Tab, перейдем в панель
данных. Вызовем локальное меню: Alt+F10. Выбираем команду Block. Появ-
ляется новое меню (на это указывает стрелка, замыкающая название команды
Block). Меню показано на рис. 4.1.

Clear...
Move...
Set...
Read...
Write...
Рис. 4.1.

Выбираем команду Write.... Появляется окно с запросом имени файла:


"Enter write file name". В поле ввода File Name введем имя файла [Link]. Имя,
разумеется, может быть любым, а вот расширение — только .com, не .exe.
Нажимаем Enter.
Появляется новое окно с запросом адреса блока памяти и количества байтов
в блоке: Enter memory address, count. Наша программа расположена, начиная с
адреса CS:0100. В панели данных подразумевается, что сегментная часть адреса
4

блока находится в регистре DS. Но в панели регистров мы видим, что содержи-


мое сегментных регистров CS и DS совпадает. Поэтому адрес блока можно за-
дать как 100 — только смещение (offset), без указания сегментной части адреса.
Количество записываемых байтов: 8h – 00FFh = 9h. Итак, в поле ввода указыва-
ем через запятую два числа: 100, 9, и нажимаем Enter.
Заметим, что если бы размер программы составил бы 2Dh, то ввод 100, 2d
был бы ошибкой: в файл было бы записано всего два байта, т.к. d — суффикс
десятичного числа. В этом случае обязательно надо указывать суффикс шестна-
дцатеричного числа: 100, 2dh.
Выход из отладчика осуществляем командой Alt+X.
Убедитесь, что в текущем каталоге действительно имеется файл [Link]
размера 9 байтов. Запускать его на выполнение из командной строки бессмыс-
ленно по двум причинам:
 программа не отображает результаты работы на экране, проследить ее
работу можно только средствами отладчика;
 в программе нет команд, обеспечивающих возврат в DOS, поэтому после
наших четырех команд начнет выполняться "мусор" с непредсказуемыми
последствиями.

4.8. Отладка программы, хранящейся в файле.


Мы хотим еще поработать с нашей программой, записанной в файле
[Link]. Начать работу можно двумя способами.
а) Укажем имя файла в командной строке при запуске Turbo Debugger:
C:\prog\>td [Link]
На экране появится окно с сообщением: Program has no symbol table (у про-
граммы нет таблицы символов). У этой программы действительно нет таблицы
символов — информации, помогающей вести отладку. Создавать эту таблицу
мы научимся позже. Нажимаем Enter, чтобы закрыть окно с этим сообщением.
Теперь можно работать с программой.
б) Вызовем Turbo Debugger
C:\prog\>td
А теперь загрузим программу с использованием главного меню: F10 → File
→ Open. В диалоговом окне Load a new program to debug (Загрузить новую про-
грамму для отладки) заменяем в поле ввода Program name строку *.exe строкой
*.com (т.е. мы будем загружать файл типа .com). Далее щелкаем по кнопке
Browse (Обзор). Выбираем из списка файл [Link]. Его имя появляется в поле
ввода. После щелчка по кнопке OK получаем уже знакомое сообщение: Program
has no symbol table.

4.9. Перемещение кода программы.


Пример. Предположим, мы набрали программу
cs:0100 mov ax,1
cs:0103 add ax,bx
cs:0105 nop
cs:0106
и обнаружили, что пропустили команду mov bx,2. Перемещаем часть про-
граммы со 103 по 105 "подальше". Затем введем недостающую команду и вер-
нем перемещенный фрагмент на новый адрес.
5

Теперь опишем эту процедуру более детально. Перейдем в панель данных.


В локальном меню: Alt+F10 → Block → Move. В нижней части экрана читаем
подсказку Copy a block of memory to a new address (копирование блока памяти
по новому адресу). Появляется диалоговое окно: Enter source address, destination,
count (Введите адрес источника, адрес назначения, количество (байтов)). Вво-
дим через запятую: 103, 400, 20. Мы не стали скрупулезно подсчитывать, сколь-
ко байтов занимает копируемый блок памяти, а взяли его «с запасом». Скопиро-
вали заодно и «мусор» в памяти, расположенный за нашей программой. Это не
страшно. Переходим в панель кода и вводим недостающую команду
cs:0103 mov bx,2
cs:0106
Теперь мы знаем адрес назначения (0106) и перемещаем «хвост» програм-
мы. Для этого переходим в панель данных и вновь выбираем в локальном меню:
Alt+F10 → Block → Move. Далее вводим: 400, 106, 20.
Заметим, что сегментные регистры CS и DS содержат одинаковые значения.
Поэтому в качестве адреса блока достаточно было указать смещение. А вот если
бы CS и DS указывали бы на разные сегменты, то пришлось бы указывать адрес
блока полностью: cs:103, cs:400, 20. Ведь мы копируем данные.
Этот пример поучителен тем, что с кодами команд мы работаем как с дан-
ными.
Упражнение. Разработайте последовательность действий, если нужно уда-
лить часть команд программы. О "перекрытии" области-приемника и области-
источника беспокоиться не нужно (проверьте!).

4.10. Как получить текст программы, набранной в TD.


После отладки внесения необходимых изменений в команды программы
хотелось бы получить файл с текстом программы, чтобы добавить в него ком-
ментарии, распечатать и т.д.
Для получения «мгновенных снимков» содержимого окон предназначено
так называемое log-окно (log — это «журнал», куда записываются события,
например, судовой журнал).
Можно рекомендовать следующую последовательность действий.
Пусть активной является панель кода. В главном меню: Edit → Dump pane
to log (скопировать содержимое панели, отображаемое на экране, в log-окно).
Перейдем в log-окно: F10 → View → Log. Мы видим в окне содержимое панели
кода. А теперь с помощью локального меню этого окна откроем log-файл
(Alt+F10 → Open log file). В диалоговом окне дадим файлу имя [Link]. Затем
выполним в локальном меню команду: Close log file. Используя редактор FAR,
вы можете удалить в файле [Link] лишние строки.
В процессе выполнения программы по шагам в log-окно можно отправлять
копии содержимого панелей несколько раз. Например, для программы, которую
мы только что рассмотрели, можно было после выполнения каждой команды
копировать в log-окно содержимое окна с регистрами и окна с флагами (попро-
буйте!). Если программа работает с памятью, то удобно записывать состояние
памяти до и после выполнения программы.

Вам также может понравиться