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

Продолжение таблицы 1.1

Изменение данных

Ctrl+C

Установить маркер на редактируемую ячейку или регистр, а затем Ctrl+C

Установка типа изменяемых данных

Ctrl+D

При редактировании ячейки памяти можно установить: byte, word и т.д.

Просмотр памяти

Ctrl+G

В диалоговом окне ввести адрес начала области просмотра

Поиск

Ctrl+S

Поиск необходимой инструкции или содержимого ячейки памяти

1.2 Порядок выполнения работы

2.1 Запустить Turbo Debugger.

2.2 Загрузить в отладчик небольшой по объему файл с расширением *.ехе.

2.3 Найти все окна, описанные в п.1.4.

2.4 Выполнить все команды приведенные в таблице.

2.5 Осуществить перевод предложенных преподавателем чисел из одной системы в другую.

2.6 Найти в теоретических сведениях или при работе с отладчиком ответы на контрольные вопросы.

1.3 Контрольные вопросы

  1. Какой диапазон чисел можно передать по 16-разрядной шине? по 32-разрядной? по 64-разрядной?

  2. Типы программ-отладчиков и особенности их работы.

  3. Основные команды для работы с ячейками памяти и регистрами отладчика Turbo Debugger ?

  4. Основные команды для отладки загруженной программы ?

Основные команды для работы с окнами отладчика Turbo Debugger

Лабораторная работа № «Создание программы в среде разработки. Команды обмена данными. Линейные программы на Ассемблер»

Цель работы: изучить назначение регистров и структуру памяти, ознакомиться со структурой программы на языке Ассемблер, знать синтаксис простейших команд и научиться составлять линейные программы на Ассемблере.

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

2.1 Теоретические сведения

2.1.1 Структура ЭВМ. Регистры

При выполнении программы, микропроцессор взаимодействует с оперативной памятью, где хранятся исполняемая программа и данные, а так же с периферийными устройствами (рисунок 2.1).

Рисунок 2.1 – Структура ЭВМ минимальной конфигурации

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

Для организации вычислений микропроцессор (для упрощения выполняемых задач в рамках лабораторных работ будет рассмотрен 16 разрядный микропроцессор i8086) имеет в своём составе 14 шестнадцатиразрядных регистров, которые обеспечивают выполнение программы.

К регистрам общего назначения относят: AX(AH, AL), BX(BH, BL), CX(CH, CL), DX(DH, DL), которые делятся программно на пары однобайтных регистров и могут использоваться для хранения данных. Разбиение на однобайтные регистры позволяет увеличить общее число регистров.

Регистры SP, BP – это указатель и база стека, соответственно, обеспечивают доступ к данным в стеке, могут использоваться для хранения данных, но делать это не рекомендуется, так как при этом возможно нарушение адресации в стеке, особенно при использовании SP.

Регистры SI, DI – шестнадцатиразрядные регистры для хранения данных.

Регистры CS, DS, ES, SS – хранят адреса сегментов в памяти, не могут использоваться для хранения данных.

Регистр IP – регистр инструкций – хранит адрес(смещение) следующей исполняемой команды.

FLAGS – регистр флагов содержит набор битовых флагов, определяющий текущее состояние процессора и результат выполнения предыдущей команды. Названия и назначение регистров-флагов приведены в таблице 2.1.

Таблица 2.1. Флаги

Флаг

Название

Назначение

О

Переполнение

Переполнение при выполнении арифметических операций

D

Направление

Направление пересылки данных при выполнении строковых команд

I

Прерывание

Разрешает/Запрещает внешние прерывания

T

Пошаговый

режим

Останов после выполнения каждой команды(используется отладчиками)

S

Знак

Знак результата выполненной команды(0 – плюс, 1 – минус)

Z

Ноль

Значение результата выполненной команды(0 – ненулевой, 1 – нулевой)

A

Внешний

перенос

Используется для специальных арифметических операций

P

Контроль

чётности

Число единиц в операнде(0 – нечётное, 1 – нечётное)

C

Перенос

Содержит перенос из старшего бита при выполнении арифметических операциях

2.1.2 Структура памяти

Память, с которой взаимодействует процессор при обработке программ, называется оперативным запоминающим устройством (ОЗУ) или random access memory (RAM). Она состоит из набора однобайтных ячеек, обращение к которым происходит по их номерам (физическим адресам). Число ячеек зависит от ширины шины адреса и составляет для процессора i8086 20 – ячеек (1Мбайт), т.к. ширина шины адреса равна 20. Для процессоров с шириной шины адреса 32 объём ОЗУ может доходить до 4 Гбайт.

Данные можно читать или сохранять в ОЗУ байтами, указывая номер требуемой ячейки или словами (2 байта), указывая адрес младшей ячейки памяти и вводя специальный префикс.

2.1.3 Сегментация памяти

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

Один из них – сегментный, он хранит адрес начала блока памяти, который и называется сегментом. Если к шестнадцати разрядам сегмента мысленно справа дописать четыре двоичных нуля(16+4=20), то получим физический адрес начала сегмента в ОЗУ. Второй регистр хранит величину смещения адреса требуемой ячейки от начала сегмента. Адрес ячейки памяти записывается в виде двойного слова (4 байта): <сегмент>:<смещение>.

Сегмент всегда начинается с ячейки, номер которой заканчивается на 4 двоичных (или один шестнадцатеричный) нуля. Минимальная длина сегмента 16 байт (параграф). Максимальная длина определяется длиной регистра, хранящего смещение и равна 216 (64 Кбайта).

Пара регистров CS:IP(<сегмент>:<смещение>) определяют адрес следующей команды программы.

Для адресации данных используются сегментные регистры DS и ES, а в качестве регистров, хранящих смещение, используются регистры общего назначения BX, SI, DI. Для работы с сегментом стека используют сегментный регистр SS и регистр BP.

2.1.4 Структура программы на языке Ассемблер

Программа на языке ассемблера представляет собой текст, разбитый на строки. Каждая строка либо соответствует машинной команде, либо является директивой ассемблера или макрокомандой. Команды и директивы можно набирать как большими, так и малыми латинскими буквами. Русские буквы можно использовать только в комментариях. Структура программы на языке Ассемблер приведена в листинге 2.1.

Листинг 2.1. Структура программы на ассемблер

<имя сегмента> segment

команды или директивы

<имя сегмента> ends

[

<имя сегмента> segment

команды или директивы

<имя сегмента> ends ]

end <метка входа в программу>

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

Каждая программа содержит сегменты данных и команд, но минимально может содержать только сегмент команд

Строка программы, в общем случае, состоит из четырех полей:

  • поля метки;

  • поля операции;

  • поля операндов;

  • поля комментариев.

Пример строки программы представлен в листинге 2.2.

Листинг 2.2. Пример строки программы

M1: Add AX, BX ; сложение

Имена данных, процедур, сегментов или метки команд могут состоять не более чем из 31 латинских букв и цифр, причем первым символом должна быть обязательно буква. Большие и маленькие буквы не различаются.

2.1.5 Директивы ассемблера

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

Синтаксис директивы задания исходных данных представлен в листинге 2.3.

Листинг 2.3. Синтаксис директивы задания исходных данных

[<имя>] d<тип> <константа> [,<константа>, <константа>, . . .]

<имя> – имя массива данных, по которому к ним можно обратиться из команды;

d (define) – определяет начало массива данных;

<тип> – размер констант, входящих в массив, может принимать следующие значения:

  1. b – байт;

  2. w – слово (два байта);

  3. d – двойное слово;

  4. q – учетверённое слово;

  5. t – десять байтов;

<константа> – числовой или символьный элемент массива дан­ных.

В ассемблере используется несколько типов констант:

  1. десятичные – последовательность цифр от 0 до 9;

  2. шестнадцатеричные – последовательность шестнадцатеричных цифр от 0 до 9 и от А или а до F или f, завершающаяся буквой H или h, первой должна быть десятичная цифра или 0;

  3. восьмеричные – последовательность цифр от 0 до 7, завершающаяся буквами Q или q;

  4. двоичные – последовательность цифр от 0 до 1, завершающаяся буквой B или b;

  5. символьные – символ или группа символов, заключённые в кавычки;

  6. знак ? – используется для резервирования места для данных.

Пример задания и одновременной инициализации массива представлен в листинге 2.4.

Листинг 2.4. Пример использования директивы задания исходных данных

MyArray1 db 123, 0a2h, 75q, 110011b, 'a', 'пример', ?, ?

Для заполнения больших массивов используется директива dup (duplicate). В примере, показанном в листинге 2.5, директива выделяет в памяти 23 · 3=69 байтов и заносит в них образец 1, 2, 'x', 1, 2, 'x'.

Листинг 2.5. Использования директивы dup

MyArray2 db 23 dup(1, 2, 'x')

Директива использования сегментных регистров по умолчанию имеет синтаксис, представленный в листинге 2.6.

Листинг 2.6. Директива assume

assume <имя сегментного регистра>:<имя сегмента или nothing>[, <имя сегментного регистра>:<имя сегмента или nothing>, …]

Как отмечалось выше, для задания адреса в памяти требуется два регистра, один из них всегда сегментный, поэтому в команде при обращении к памяти приходиться набирать имя сегментного регистра, часто одного и того же. Директива assume позволяет избежать этого. Транслятор сопоставляет имя массива данных и автоматически подставляет сегментный регистр, заданный для сегмента, в котором расположен данный массив. Слово nothing показывает, что данный сегментный регистр не адресуется по умолчанию. Директива assume может использоваться в программе при каждом изменении сегмента для данного сегментного регистра, но обязательно в начале сегмента, где она задаёт по умолчанию сегментный регистр для сегмента кодов. Пример показан в листинге 2.7.

Листинг 2.7. Пример использования директивы assume

assume cs:code, ds:data, es:nothing

Здесь code и data – имена сегментов кодов и данных, соответственно, а сегментный регистр es не адресуется по уполчанию.

2.1.6 Режимы адресации

Способ определения операнда называется режимом адресации. Различают следующие режимы адресации.

Регистровая прямая – операнд находится в регистре. Например: mov АХ,SI. Данная запись означает – переслать содержимое регистра SI в регистр АХ.

Непосредственная – непосредственный операнд (константа) присутствует в команде. Например: mov AX, 093Ah – означает: занести константу 093Ah в регистр АХ.

Прямая – исполнительный адрес операнда присутствует в команде. Например, mov AX,WW – означает: переслать в АХ слово памяти с именем WW, а выражение: mov BX,WW+2 переслать в ВХ слово памяти отстоящее от переменной с именем WW на 2 байта.

Регистровая косвенная - регистр содержит адрес операнда. Выражение mov[BX],CL – означает переслать содержимое регистра CL по адресу, находящемуся в регистре ВХ.

Регистровая относительная – адрес операнда вычисляется как сумма содержимого регистра и смещения: mov АХ,WW[SI] – переслать в АХ слово из памяти, адрес которого вычисляется как сумма содержимого регистра SI и смещения WW.

Индексно-базовая – адрес операнда вычисляется как сумма содержимых базового и индексного регистров и смещения: mov [BX+ SI+ 2],CL – переслать содержимое регистра CL по адресу, вы­числяемому как сумма содержимого регистров ВХ, SI и константы 2.

2.1.7 Инструкции пересылки данных и двоичной арифметики

Команды данной группы приведены в таблице 2.2. Код определяет выполняемое командой действие, операнды показывают адреса ячеек, хранящих исходные данные, необходимые для выполнения команды и адрес ячейки результата. Процессор i8086 и более поздние версии относятся к двухадресным машинам. Это значит, что его команда может содержать не более двух операндов. Если для выполнения команды необходимо иметь два источника данных, например, сложение, то сохранение результата выполнения команды производиться по адресу одного из источников данных. Чтобы показать, какой из операндов будет хранить результат, его обозначают при описании команды как dst (destination – назначение), операнд, который используется только как адрес исходных данных, обозначается как src (source – источник). В двухоперандных командах операнд dst указывает, перед выполнением команды, адрес исходного данного, а после выполнения – адрес результата.

Таблица 2.2. Основные операторы Ассемблера

Мнемокод

Флаги

Действие

Код

Операнды

O

S

Z

A

P

C

mov

dst, src.

-

-

-

-

-

-

пересылка

хchg

dst, src

-

-

-

-

-

-

обмен

add

dst, src

х

х

х

х

х

х

сложение

adc

dst, src

х

х

х

х

х

х

сложение с переносом

inc

dst

х

х

х

х

х

-

увеличить на единицу

sub

dst, src

х

х

х

х

х

х

вычитание

sbb

dst, src

х

х

х

х

х

х

вычитание с заемом

dec

dst

х

х

х

х

х

-

уменьшение на единицу

neg

dst

х

х

х

х

х

х

изменение знака

rcl

dst,счетчик

х

-

-

-

-

х

циклический сдвиг влево

rcr

dst,счетчик

х

-

-

-

-

х

циклический сдвиг вправо

rol

dst,счетчик

х

-

-

-

-

х

циклический сдвиг влево

ror

dst,счетчик

х

-

-

-

-

х

циклический сдвиг вправо

sal

dst,счетчик

х

х

х

u

х

х

арифметический сдвиг влево

sar

dst,счетчик

х

х

х

u

х

х

арифметический сдвиг вправо

shl

dst,счетчик

х

х

х

u

х

х

логический сдвиг влево

shp

dst,счетчик

х

х

х

u

х

х

логический сдвиг вправо

push

src

-

-

-

-

-

-

сохранение слова в стеке

pop

dst

-

-

-

-

-

-

восстановление слова из стека

xlat

таблица

-

-

-

-

-

-

трансляция байтов из таблицы

lea

dst, src

-

-

-

-

-

-

загрузка исполнительного адреса

lds

dst, src

-

-

-

-

-

-

загрузка указателя с DS

les

dst, src

-

-

-

-

-

-

загрузка указателя с ES

lahf

-

-

-

-

-

-

загрузка флагов в АН

sahf

-

r

r

r

r

r

установка флагов из АН

pushf

х

-

-

-

-

х

сохранение флагов в стеке

popf

r

r

r

r

r

r

восстановление флагов из стека

Примечание:

- флажок не модифицируется

х устанавливается или сбрасывается в соответствии с результатом

u не определен

r восстанавливается прежнее запомненное значение

2.1.8 Запись программ на языке ассемблера

В листинге 2.8 приведена типичная структура простой программы на ассемблере.

Листинг 2.8. Пример программы

data segment ;директива начала сегмента данных

d1 dw 34h ;переменная d1 имеет размер

;2 байта и содержит значение 52

d2 db 10100110b ;переменная d2 имеет размер

;1 байт и содержит значение 166

d3 dd 3 dup (?) ;массив d3 содержит 3 элемента

;по 4 байта, содержащих случайные

;значения (возможно нулевые)

data ends ;директива конца сегмента данных

code segment ;директива начала сегмента кода

assume cs: code, ds: data ;задание сегментных регистров

start: mov ax,data ;загрузка адреса

mov ds,ax ;сегмента данных в регистр ds

.

.

. ;текст программы

quit: mov ax,4c00h ;код завершения 0

int 21h ;выход в DOS

code ends ;директива конца сегмента кода

end start ;конец трансляции программы

Загрузка адреса сегмента данных состоит из двух команд, так как непосредственные данные нельзя заносить прямо в сегментный регистр.

Для завершения программы и выхода в DOS имеется несколько возможностей, рекомендуется использовать две команды, начинающиеся с метки quit.

2.1.9 Обработка программ в MS-DOS

Обработка программ на языке ассемблера в MS-DOS состоит из следующих этапов:

1) создать с помощью текстового редактора файл с текстом программы на языке ассемблера;

2) транслировать программу с помощью ассемблера TASM (или MASM);

3) Скомпоновать программу с помощью компоновщика (редактора связей) TLINK(или LINK);

4) Запустить программу на выполнение (через отладчик).

Файл исходного текста программы должен иметь расширение *.asm.

Запуск транслятора осуществляется командой: tasm <исходный файл >.

При этом будет создан объектный файл (*.obj).

Компоновщик использует объектный файл и создаёт исполняемый файл с расширением по умолчанию *.exe. Запуск компоновщика осуществляется командой: link < объектный файл >.

Для запуска под отладчиком необходимо запустить отладчик и загрузить исполняемый файл.

2.2 Пример выполнения работы

Задание: Вычислить Х = 3А+(В+5)/2–С–1, где А,В,С,Х – целые знаковые числа занимающие слово. Написать программу, реализующую данную формулу.

Распишем формулу по отдельным операциям:

АХ ← А ; значение А в регистре АХ

АХ ← 2*(АХ) ; значение 2А в регистре АХ

АХ ← (АХ) + А ; значение 3А в регистре АХ

ВХ ← В ; значение В в регистре ВХ

ВХ ← 5 + (ВХ) ; значение (В+5) в регистре ВХ

ВХ ← (ВХ)/2 ; значение (В+5)/2 в регистре ВХ

АХ ← (BX)+(AX) ; значение 3А+(В+5)/2 в регистре АХ

АХ ← (АХ)–С ; значение 3А+(В+5)/2–С в регистре АХ

АХ ← (АХ)–1 ; значение 3А+(В+5)/2–С–1 в регистре АХ

Х ← (АХ) ; значение 3А+(В+5)/2–С–1 в регистре Х

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

Листинг 2.9. Пример программы

data segment

a dw 10

b dw 20

c dw 5

x dw ?

data ends

code segment

assume cs: code, ds: data

start: mov ax, data

mov ds, ax

mov ax, a

sal ax, 1

add ax, a

mov bx, b

add bx, 5

sar bx, 1

add ax, bx

sub ax, c

dec ax

mov x, ax

quit:

mov ax, 4c00h

int 21

code ends

end start

2.3 Варианты заданий

Разработать программу, реализующую указанную формулу (переменные в программе имеют размер слова). Проверить работоспособность программы на нулевом, единичном и произвольном наборах входных данных. Объяснить полученные результаты. Подтвердить полученные значения расчетами вручную или на калькуляторе.

Блок 1.

  1. Х= 4А–3В+С/4

  2. Х= 6А-5*(В+С)/2–1

  3. Х= (А+2В–С)/4

  4. Х= (С–А)/2+(В+С)/8

  5. Х= (4А–7В–32С)/2

  6. Х= – (–(С+2А)*5+В)

  7. Х= 3*(А–2В)+50–С/2

  8. Х= (3А+2В) –С/4+217

  9. Х= 3*(С–2A)+(В–С+1)/2

  10. Х= (2А+В)/4–С/2+168

  11. Х= 6*(А-2В+С/4)+10

  12. Х= 3*(А–4В)+С/4

  13. Х= – (– (С +2А)*5+В*16)

  14. Х= А/2–3*(А+В)+С*4

  15. Х= 3*(А–2В)+50–С/2

  16. Х= 5А+2В–С/4+131

  17. Х= А–5*(В–2С)+2

  18. Х= –4А+(В+С)/4+2

  19. Х= 7А–2В–100+С/2

  20. Х= –А /2+4*(В+1)+3С

  21. Х= 5*(А–В) –2С+5

  22. Х= (А/2+В)/4+С–1

  23. Х= – (С+2А+4В)+18

  24. Х= 6А+(В–С+1)/2

  25. Х= 2–8*(А+В)+С/4