Меню сайта

Урок 77. Управление циклами

Существует несколько команд условногоперехода, предназначенных для
— — — управления циклами в программах. — Поскольку программые циклы
— — — используются часто, желательно эффективноеуправление циклом. — На
— — — Фиг. 4.30 показаны четыре команды,созданные для того, чтобы
— — — облегчить программирование циклов на языкеассемблера
— — — микропроцессора 8088.

— — — — — Так же, как строковые команды используютрегистр CX в качестве
— — — счетчика, команды цикла LOOP используютрегистр CX в качестве
— — — счетчика цикла. Все эти команды неявнорассматривают регистр CX как
— — — счетчик итераций цикла. Простейшая командасреди них — команда
— — — LOOP. Команда LOOP уменьшает регистр CX ипередает управление на
— — — метку, если содержимое регистра CX неравно 0. Если вычитание
— — — единицы из регистра CX не привело кнулевому результату, команда
— — — LOOP не делает перехода, и выполняетсяследующая команда.

— — — — — Приведенный ниже программный фрагментдемонстрирует обычное
— — — использование команды LOOP.

— — — — — MOV — — -CX,LOOP_COUNT
— — — — — BEGIN_LOOP:
— — — — — — … -тело цикла
— — — — — LOOP — -BEGIN_LOOP

— — — — — — — -Microsoft (R) Macro Assembler Version 5.00 — — — — — — — — — — — — — 1/1/80 04:02:01
— — — — — — — -Фиг. 4.30 Команды цикла — — — — — — — — — — — — — — — — — — — — — — — — — — Page — 1-1


— — — — — — — — — — — — — — — — — — — — — — — — — — — — — — — — — — — — — — PAGE — — -,132
— — — — — — — — — — — — — — — — — — — — — — — — — — — — — — — — — — — — — — TITLE — -Фиг. 4.30 Команды цикла

— — — — — — — — -0000 — — — — — — — — — — — — — — — — — CODE — — -SEGMENT
— — — — — — — — — — — — — — — — — — — — — — — — — — — — — — — — — — — — — — ASSUME -CS:CODE

— — — — — — — — — — — — — — — — — — — — — — — — — — — — — — — — ——————————————
— — — — — — — — — — — — — — — — — — — — — — — — — — — — — — — — — В этом примере демонстрируются командыцикла.
— — — — — — — — — — — — — — — — — — — — — — — — — — — — — — — — — Команды в примере не являютсязаконченной программой.
— — — — — — — — — — — — — — — — — — — — — — — — — — — — — — — — ——————————————

— — — — — — — — -0000 — E3 06 — — — — — — — — — — — — — — — — JCXZ — — — END_OF_LOOP — — — — — Конец цикла, если CX равно 0

— — — — — — — — -0002 — — — — — — — — — — — — — — — — — BEGIN_LOOP:

— — — — — — — — — — — — — — — — — — — — — — — — — — — — — — — — — …. -Тело цикла

— — — — — — — — -0002 — E2 FE — — — — — — — — — — — — — — — — LOOP — — — BEGIN_LOOP — — — — -Переход пока регистр CX не станет равен 0

— — — — — — — — — — — — — — — — — — — — — — — — — — — — — — — — — …. -Если проверяется какое-либо условие, то
— — — — — — — — -0004 — E1 FC — — — — — — — — — — — — — — — — LOOPE — — BEGIN_LOOP — — — — -Переход по равенству в условии и
— — — — — — — — — — — — — — — — — — — — — — — — — — — — — — — — — — — — — — — — — — — — — — — — — — — — — — — — — -значение регистра CX не равно 0
— — — — — — — — — — — — — — — — — — — — — — — — — — — — — — — — — …. -Или

— — — — — — — — -0006 — E0 FA — — — — — — — — — — — — — — — — LOOPNE — BEGIN_LOOP — — — — -Переход по неравенству в условиии и
— — — — — — — — — — — — — — — — — — — — — — — — — — — — — — — — — — — — — — — — — — — — — — — — — — — — — — — — — -значение регистра CX не равно 0

— — — — — — — — -0008 — — — — — — — — — — — — — — — — — END_OF_LOOP:

— — — — — — — — -0008 — — — — — — — — — — — — — —
— — — CODE — — -ENDS
— — — — — — — — — — — — — — — — — — — — — — — — — — — — — — — — — — — — — — END

— — — — — — — — — — — Фиг. 4.30 Команда цикла

— — — — — Программа помещает число итераций цикла врегистр CX перед
— — — выполнением цикла. Затем выполняется телоцикла, а следом за ним
— — — команда LOOP. Она уменьшает счетчик наединицу, что соответствует
— — — единственной, только что выполненнойитерации цикла. Если теперь
— — — счетчик в регистре CX равен 0, программа продолжаетвыполняться
— — — после команды LOOP. Если счетчик не равен0, управление
— — — возвращается к началу цикла, чтобысовершить еще один проход по
— — — телу цикла. Тело цикла выполняется столькораз, сколько было
— — — сначала задано содержимым регистра CX.Единственное важное
— — — замечание: если программа внутри циклаизменяет регистр CX, число
— — — итераций цикла не будет соответствоватьначальному значению в
— — — регистре CX.

— — — — — Описанный метод одинаково хорошо работает,когда число циклов
— — — известно во время ассемблирования (как впримере, где LOOP_COUNT —
— — — непосредственно заносимое значение), икогда число циклов
— — — определяется во время выполнения. Есливычисленное число оказалось
— — — равным 0, цикл выполнится 65536 раз. Когдамикропроцессор 8088
— — — выполняет первую команду LOOP, онуменьшает CX от 0 до 0FFFFH, и
— — — поскольку теперь регистр CX ненулевой,повторяет цикл. Таким
— — — образом, загрузка нулевого значениясчетчика циклов — специальный
— — — случай. Этот специальный случай обрабатываетсякомандой JCXZ
— — — (переход, если содержимое регистра CXравно 0). Эта команда
— — — проверяет текущее содержимое регистра CX,и делает переход, если
— — — оно равно нулю. Команда не проверяет ниодного флага, и не влияет
— — — ни на один из них. Следующий примераналогичен предыдущему, за
— — — исключением того, что он загружает регистрCX из ячейки памяти,
— — — содержимое которой вычисляется во времявыполнения программы. По
— — — этой причине может оказаться, что счетчикциклов нулевой, и пример
— — — использует команду JCXZ, чтобы проверить,нужно ли полностью
— — — пропустить тело цикла.

— — — — — — -MOV — — — — — — — CX,LOOP_COUNT_WORD
— — — — — — -JCXZ — — — END_OF_LOOP
— — — — — BEGIN_LOOP:
— — — — — — — — — … тело цикла
— — — — — — -LOOP — — — BEGIN_LOOP
— — — — — END_OF_LOOP:

— — — — — В программе не нужно использовать командуJCXZ в каждом цикле с
— — — вычисляемым счетчиком. Если программистзнает, что счетчик циклов
— — — никогда не будет равен нулю, проверка ненужна. Однако опыт
— — — показывает, что значение, которое»никогда» не должно появиться,
— — — обычно появляется в первую очередь, кактолько вы начинаете
— — — выполнять программу.

— — — — — Оставшиеся две команды цикла предоставляютеще большие
— — — возможностей при управлении циклами. Этикоманды аналогичны
— — — префиксам REPE и REPNE. Если команда LOOPвыходит из цикла, только
— — — когда в регистре CX оказывается нуль, токоманда LOOPE (цикл, пока
— — — равно) выходит из цикла, если установленфлаг нуля, или если в
— — — регистре CX получился 0. Тем самымстановится возможным
— — — двойственное завершение цикла. Программаможет загрузить в регистр
— — — CX максимальное число итераций цикла, азатем проверять флаг нуля в
— — — конце каждого цикла на условие завершения.Команда LOOPNE (цикл,
— — — пока не равно) выполняет обратную кописанной проверку флага нуля:
— — — цикл здесь завершается, если регистрдостиг нуля, или если
— — — установлен флаг нуля.
— — — — — Следующий пример показывает использованиекоманды LOOPNE. В
— — — примере складываются два списка чисел,чтобы найти пару элементов,
— — — сумма которых точно равна 100. Так как вкаждой итерации перед
— — — проверкой складываются два чила, командуREPNE CMPSB использовать
— — — нельзя.

— — — — — В примере предполагается, что парырегистров DS:SI и ES:DI
— — — инициализированы так, чтобы указывать наэти списки.

— — — — — MOV — — CX,MAX_LOOP_COUNT-максимальное число заходов
— — — — — BEGIN_LOOP:
— — — — — LODSB — — — — — — — —
— — — — — -чтение числа из первого списка
— — — — — ADD — — AL,ES:[DI] — —прибавить из второго списка
— — — — — INC — — DI — — — — — — — — — —указатель на следующий элемент
— — — — — CMP — — AL,100 — — — — — — — — — — — —проверка на нужное значение
— — — — — LOOPNE — — — — — BEGIN_LOOP — —снова, если не равно и не все
— — — — — JE — — — MATCH_FOUND — — — -переход сюда, чтобы определить конец

Категория: Программирование на Ассемблере | Дата: 02.02.13

Меню раздела
Блок