lect_9.ppt
- Количество слайдов: 21
ЛЕКЦИЯ № 9 ПЕРЕДАЧА УПРАВЛЕНИЯ При программировании нелинейных алгоритмов необходимо в определенных случаях изменять порядок выполнения команд путем передачи управления командам не расположенным непосредственно друг за другом в одном сегменте кода. Такая передача осуществляется: • командами передачи управления; • вызовом процедур. Команды передачи управления подразделяют на: • команды безусловного перехода; • команды условного перехода. Для указания места, в которое передается управление используются метки. Метка – Это символическое имя, обозначающее определенную ячейку памяти, предназначенное для использования в качестве операнда в командах передачи управления.
Синтаксис, типы и правила использования меток Атрибуты меток, присваиваемые транслятором: • имя сегмента кода, в котором эта метка описана; • смещение – расстояние в байтах от начала сегмента кода, в котором эта метка описана; • тип метки, или атрибут расстояния. Атрибуты расстояния: • near – переход на метку возможен только в пределах текущего сегмента кода; для перехода достаточно изменить только содержимое регистра eip/ip; • far – переход возможен только путем межсегментной передачи управления; для осуществления перехода требуется изменение содержимого регистра cs, Способы определения меток • оператором : (двоеточие); • директивой label.
Синтаксис описания метки оператором : Символическое имя : Команда ассемблера Таким способом можно задавать только метки ближнего типа: near. Синтаксис описания метки директивой label Символическое имя label Тип метки может принимать значения far или near. Пример m 1: mov ax, pol_1 m 1 label near mov ax, pol_1
Пример использования для одной и той же команды меток разных типов ; … public … mfar mnear: mfar label far mov ax, pole 1 … Пример использования директивы label для доступа к одной области памяти, как области, содержащей данные разных типов … masb masw … mov … label byte dw 15 dup (? ) masb+10, al ; записать в 11 -й байт массива байтов из al masw, ax ; записать из ax в первое слово области
Счетчик адреса команд Транслятор обеспечивает две возможности использования счетчика адреса: • использование меток, атрибуту смещения которых транслятор присваивает значение счетчика адреса той команды, перед которой она появилась; • применение специального символа $. Этот символ позволяет в любом месте программы использовать численное значение счетчика адреса. Пример использования счетчика адреса для вычисления длины строки …. data Str. Mes db “Строка данных” Len. Str=$-Str. Mes … Для задания требуемого значения счетчика адреса используется директива org выражение
Пример использования директивы org при оформления программы для формата. com codeseg segment para “code” assume cs: codeseg, ds: codeseg, ss: codeseg org 100 h jmp m 1 ; здесь описываются данные m 1: ; далее идут команды программы … Команда безусловного перехода jmp [модификатор] адрес_перехода Команды перехода модифицируют регистр указателя команды eip/ip и, возможно, сегментный регистр кода cs. Что именно модифицируется определяется : • типом операнда адрес_перехода; • значением модификатора модификатор.
В системе команд микропроцессора есть несколько кодов машинных команд jmp. Их различия определяются дальностью перехода и способом задания целевого адреса. По дальности различают: • внутрисегментный или близкий переход; • межсегментный или дальний переход. По способу задания целевого адреса различают: • прямой переход; • косвенный переход. Внутрисегментный переход предполагает, что изменяется только содержимое регистра eip/ip. Прямой короткий внутрисегментный переход. Применяется когда расстояние от команды jmp до адреса_перехода не более, чем -128 или +127 байтов. В этом случае транслятор генерирует команду длиной 2 байта (размер обычной команды внутрисегментного безусловного перехода – 3 байта). В качестве особенности следует иметь в виду, что при расположении адреса перехода после команды jmp необходимо использовать модификатор short ptr.
Пример … jmp short ptr m 1 …; не более 35 -40 команд (127 б. ) m 1: … … m 1: …; не более 35 -40 команд (-128 б. ) jmp m 1 … Прямой внутрисегментный переход. Длина машинной команды 3 байта. Увеличение длины связано с тем, что поле адреса перехода машинной команды расширяется до двух байтов. Это позволяет производить переходы в пределах 64 Кб. Пример m 1: …; расстояние >128 б и < 64 Кб … jmp m 1
Косвенный внутрисегментный переход В команде указывается не сам адрес перехода, а «место» , где он лежит: регистр или область памяти. Пример 1 … lea bx, m 1 jmp bx ; адрес перехода в регистре bx … m 1: … Пример 2 …. data addrm 1 dw m 1 …. code … jmp addrm 1 ; адрес перехода в ячейке addrm 1 … m 1: …
Пример 3. data addr dw dw ( Переход одной командой на разные метки) m 1 m 2 …. code … cycl: mov jmp si, 0 addr[si] ; алрес перехода в слове памяти addr+(si) mov jmp si, 2 cycl … m 1: … m 2: ….
Пример 4 …. data addr dw m 1 …. code … lea si, addr jmp near ptr [si] ; адрес перехода в ячейке памяти addr … m 1: … В этом случае обязательно использование модификатора near ptr, так как адрес ячейки памяти addr с адресом перехода передается неявно, поэтому транслятору неясно, о каком переходе может идти речь: о внутрисегментном или межсегментном.
Межсегментный переход предполагает другой формат машинной команды jmp. При осуществлении такого перехода модифицируется кроме регистра eip/ip регистр cs. Прямой межсегментный переход. Длина машинной команды 5 байтов, из которых два байта для смещения адреса перехода два байта для сегментной составляющей адреса. Пример seg 1 … segment jmp far ptr m 2 ; здесь far обязательно … m 1 label far … seg 1 ends seg 2 segment … m 2 label far jmp m 1 … ; здесь far необязательно
Косвенный межсегментный переход. В качестве операнда выступает в явной или неявной форме адрес области памяти, в которой хранится сегментная составляющая и смещение целевого адреса перехода. Пример1 data segment addrm 1 dd m 1 ; в поле addrm 1 полный адрес метки m 1 data ends code 1 segment … jmp addrm 1 … code 1 ends code 2 segment … m 1 label far mov ax, bx … code 2 ends
Пример 2 (косвенный регистровый межсегментный переход) data segment addrm 1 dd m 1 data ends code 1 segment … lea bx, addrm 1 jmp dword ptr[bx] ; использование модификатора обязательно! … code 1 ends code 2 segment … m 1 label far mov ax, bx … code 2 ends
ПРОЦЕДУРЫ Процедура или подпрограмма представляет собой группу команд для решения конкретной подзадачи и обладает средствами получения управления из точки вызова задачи более высокого уровня и возврата управления в эту точку. Для описания последовательности команд в виде процедуры в ассемблере используются директивы: PROC и ENDPROC. Среди большого количества атрибутов директивы PROC обязательно использование только одного – имени процедуры. Часто используются также атрибут расстояние, который может принимать значения far либо near. Используются следующие варианты размещения процедуры в программе: • в начале программы (до первой исполняемой команды; • в конце (после команды, возвращающей управление операционной системе; • внутри основной программы с обязательным использованием команды jmp для обхода процедуры;
• в отдельном модуле. Пример 1 model small. stack 100 h. data. code myproc near … ret myproc endp start: … end start Объявление имени процедуры в программе равносильно объявлению метки. Поэтому сама исполняемая программа также может быть оформлена в виде процедуры, что определяет точку входа в программу как первую команду, следующую за директивой PROC. При этом имя этой процедуры долджно быть обязательно указано в заключительной директиве END.
Пример 2 model small. stack 100 h. data. code myproc near … ret myproc endp start proc … start endp end start После загрузки в память управление будет передано первой команде процедуры с именем start.
Пример 3 model small. stack 100 h. data. code start: … mov ax, 4 c 00 h int 21 h ; возврат управления операционной системе myproc near … ret myproc endp end start
Пример 4 model small. stack 100 h. data. code start: … jmp m 1 ; обход процедуры myproc near … ret myproc endp m 1: … mov ax, 4 c 00 h int 21 h ; возврат управления операционной системе end start
Так как имя процедуры обладает теми же свойствами, что и обычная метка, то обратиться к процедуре можно, в принципе, с помощью любой команды перехода. Однако для того, чтобы воспользоваться механизмом сохранения контекста программы нужно воспользоваться командой call [модификатор] имя_процедуры Эта команда передает управление по адресу с символическим именем имя_процедуры, но при этом в стеке сохраняется адрес возврата – адрес следующей за call команды. возвращение управления вызывающей программе с автоматическим восстановлением контекста осуществляется командой ret [число] Необязательный параметр число обозначает количество элементов, удаляемых из стека при возврате из процедуры. Размер элемента определяется параметром директивы segment (use 16 или use 32). В первом случае число – это значение в байтах, во втором случае – в словах.
Как и для команды jmp, для команды call актуальна проблема организации ближнего и дальнего вызова (внутрисегментного и межсегментного). В первом случае по команде call в качестве адреса возврата в стеке сохраняется значение регистра-указателя команд eip/ip, во втором случае в стеке сохраняется значение двух регистров: cs и eip/ip. Общие правила оформления ближних и дальних вызовов с использованием команды call такие же, как и для команды jmp.


