Optron #28
08 июня 1999

Ликбез - Ассемблер взгляд издалека: Команды единичного приращения, прямой и относительный переход, организация цикла.

<b>Ликбез</b> - Ассемблер взгляд издалека: Команды единичного приращения, прямой и относительный переход, организация цикла.
       Ассемблер: взгляд издалека.

  Продолжение. Начало в ||20, 21, 24, 25

{}Инфарх, 1999

      Команды единичного приращения

  В  самой первой статье нашего "Ликбекза"
как  пример команды Ассемблера упоминалась
команда   приращения  INC.  Настало  время
вплотную заняться ею, а также её "напарни-
цей" - командой DEC (от англ."decrement" -
многократное  уменьшение значения перемен-
ной на заданную постоянную величину).
  Никак нельзя приуменьшить  их  важности!
Ведь  если вам вдруг понадобится увеличить
или  уменьшить содержимое некоего регистра
или  регистровой  пары  на единицу, то что
делать:    работать    с   арифметическими
действиями? Упаси Господь!
  И здесь нам на помощь приходят эти самые
команды  положительного  и  отрицательного
единичного приращения. Рассмотрим варианты
их использования, не забыв и о флагах:

   ╔═════════════╤═══════════════════╗
   ║  МНЕМОНИКА  │Разряды регистра F ║
   ║             │     (флаги)       ║
   ╟────┬────────┼───────────────────╢
   ║Опе-│        │                   ║
   ║ ра-│Операнд │ C  Z P/V S  N  H  ║
   ║ ция│        │                   ║
   ╟────┴────────┼───────────────────╢
   ║ DEC r       │ .  x  V  x  1  x  ║
   ║ DEC (HL)    │                   ║
   ║ DEC (ii+n)  │                   ║
   ║ DEC rr      │ .  .  .  .  .  .  ║
   ║ DEC ii      │                   ║
   ║             │                   ║
   ║ INC r       │ .  x  V  x  0  x  ║
   ║ INC (HL)    │                   ║
   ║ INC (ii+n)  │                   ║
   ║ INC rr      │ .  .  .  .  .  .  ║
   ║ INC ii      │                   ║
   ╚═════════════╧═══════════════════╝

  Обозначения -   аналогично    предыдущим
статьям "Ликбеза".

  Хоть команда и предельно проста, рассмо-
трим пример.  Перед вами - фрагмент  прог-
раммы:

     LD   A,5
     LD   HL,#C000
     LD   (HL),A
     INC  HL
     DEC  A
     LD   (HL),A

  Первые три строки понятны: в "А" записы-
вется  число 5,  в регистровую пару "HL" -
число #C000.  Затем  происходит  пересылка
содержимого "А" по адресу (HL), после чего
содержимое байта по адресу #C000 равно пя-
ти.
  Следующая  строка  содержит команду "INC
HL", после выполнения которой в "HL" будет
уже  число  #C001.  Соответственно,  после
"DEC A" в аккумуляторе окажется уже не пя-
тёрка,  а  четвёрка, которая следующей ко-
мандой  будет  переслана  по адресу (HL) -
#C001. Вот так можно легко задавать прира-
щения  для  регистров,  регистровых  пар и
байтов,  адресуемых  через  "HL", "IX" или
"IY".


          Продолжим воспоминания

  Из наших  предыдущих занятий у вас могло
создаться превратное впечатление, что про-
цессор Z80 выполняет свои команды последо-
вательно одну за другой без всяких  прочих
вариантов.
  Но это далеко не так!
  Конечно, команды  следуют своей чередой.
Но что управляет этим процессом?
  Припомните прошлые занятия - регистр PC,
он  же - программный счётчик. В нём сохра-
няется  адрес  той команды, которая должна
выполняться.  Процессор, обрабатывая опре-
делённую команду в ячейке памяти, адресуе-
мой  через  PC,  автоматически увеличивает
его  на единицу. Таким образом, содержимое
PC постоянно модифицируется в процессе ра-
боты программы.
  А если мы  захотим  изменить  последова-
тельность  выполнения  команд в программе,
то нам достаточно изменить содержимое  PC.
И сделать это можно при помощи манипуляций
с  битами и проверки состояния бита и бай-
та,  о чём в прошлый раз у нас и шла речь.
Пора  применить  полученные знания в деле.
Итак...


              Прямой переход

  Есть у процессора такая команда,  как JP
(от англ.  jump - прыжок, переход). За ней
следует  двухбайтный параметр:  адрес,  на
который мы хотим  сделать  переход.  Когда
процессор встретит команду JP,  он возьмёт
следующий за ней адрес,  поместит его в PC
и...  перейдёт  к выполнению следующей ко-
манды - той, чей адрес он только что полу-
чил.
  Адрес перехода не обязательно должен на-
ходиться непосредственно в  памяти  следом
за JP.  С не меньшим успехом им может быть
содержимое регистровых пар HL, IX, IY. Ко-
манда записывается следующим образом:

  JP nn
  JP cc,nn
  JP (HL)
  JP (ii)

  - А  что  это за "cc" такое? - можете вы
спросить.
  А это - ни что иное,  как  условие.  Да,
команда  перехода может быть не только бе-
зусловной!  Вспомните таблицу из  прошлого
нашего  урока: была там такая колонка, как
"мнемоника  условия".  Вот  её  мы здесь и
применяем. Например:

  Адрес        Команда

  #6000        JP  C,#C003
  #6003        JP  (HL)

  Представим себе, что в PC записано число
#6000  и процессор приступает к выполнению
команды. По ходу дела PC увеличится на три
(именно   столько  байт  занимает  команда
JP C,#C003). В процессе этого будет прове-
рено,  выполняется  ли  условие "C". А оно
выполняется,  если  CY=1. После выполнения
команды  Z80  помещает  слово #C003 в PC и
начинает  выполнять следующую команду, ко-
торая   теперь  уже  находится  по  адресу
#C003.
  А если условие не выполнено (CY=0)? Тог-
да процессор никаких новых данных помещать
в  PC не будет, и следующая команда, кото-
рую  Z80  будет  выполнять, расположена по
адресу  #6003.  И команда эта представляет
собой  всё тот же переход, но теперь ника-
ких условий проверяться не будет, в PC бу-
дет  переписано  содержимое  "HL", туда же
будет и переход.
  Упомянув  условие "С", скажем и oбо всех
остальных.  Вот  какие  мнемоники  условий
можно использовать в команде "JP cc,nn":

       C, NC, Z, NZ, M, P, PE, PO.

  Сложного ничего в них нет. Рассмотрим их
все по порядку:

Z  - ноль (флаг Z установлен)
NZ - не ноль (флаг Z сброшен)
C  - перенос (флаг C установлен)
NC - нет переноса (флаг C сброшен)
M  - отрицательный результат (флаг S уста-
     новлен)
P  - положительный результат (флаг S сбро-
     шен)
PE - чётность или перепонение  (установлен
     флаг P/V)
PO - нет чётности/переполнения  (флаг  P/V
     сброшен)

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


          Относительный переход

  Этот переход отличается от прямого  тем,
что в команде задаётся не прямой адрес,  а
смещение,  которое процессор не записывает
в PC, а прибавляет к нему. Причём в данном
случае смещение  может  быть  представлено
как  положительным,  так  и  отрицательным
числом  (вспомните урок в  "Оптроне" |21),
так  что  переход может быть осуществлён в
любом направлении от команды.
  Записывается команда так:

  JR e
  JR cc,e

  Мнемоника JR  происходит  от английского
"jump relative",  что и означает  "Относи-
тельный переход".
  Обратите внимание на  параметр  команды:
"e". Он означает величину смещения относи-
тельно содержимого PC.  Как видите,  и эта
команда может быть условной. Правила здесь
действут  аналогичные  "JP",  но вот набор
возможных условий несколько меньше. Прове-
ряются только C, NC, Z, NZ.
  Рассмотрим механизм  действия команды JR
в условном варианте:

  Адрес      Команда

  #6000      JR NC,2
  #6002      LD A,5
  #6004      .......

  Итак, Z80 приступает к выполнению коман-
ды  по  адресу #6000.  Поскольку она двух-
байтная,  PC  будет  увеличен на 2 и после
выполнения  команды  будет  равен #6002. В
процессе выполнения команды процессор про-
веряет  условие  NC на истинность. Теперь,
если  CY=0, то к программному счётчику бу-
дет прибавлен ещё и параметр команды JR (в
данном случае  2), операция "LD A,5" будет
пропущена,  и следующей выполняемой коман-
дой будет  та,  что  находится  по  адресу
#6004.
  А какой вообще смысл  в  такой  команде?
Чем она отличается от JP?  Всё очень прос-
то. Ведь команда JP оперирует с прямым ад-
ресом  и  занимает в памяти три байта.  Но
иногда переход должен быть  произведён  на
небольшое  расстояние  (как в нашем приме-
ре).  Тогда  нет смысла расходовать лишний
байт  на  полный адрес, если вполне доста-
точно  диапазона  +128...-127. Кроме того,
команды  условного перехода могут быть по-
лезны и при написании так называемых рело-
цируемых  процедур, для которых адрес раз-
мещения  в памяти не имеет никакого значе-
ния  (до  этих процедур мы ещё доберёмся -
всему своё время).
  К сему  добавлю маленький вопрос:  а что
будет,  если в нашем  примере  вместо  "2"
поставить "-2"?
  И напоследок, как водится, о влиянии ко-
манд  "JR" и "JP" на флаги.  Так вот - все
эти команды абслютно никакого  влияния  на
флаги не оказывают!


            Организация цикла

  Рассмотрим случай,  когда нам необходимо
организовать циклическое выполнение  неко-
торого участка программы. Пусть в регистре
"B" хранится количество повторов. Итак...

         LD   B,5
 LOOP    ........
           тело
           цикла
         ........
         DEC  B
         JR   NZ,LOOP

  Приведённый фрагмент может поначалу выз-
вать  некоторое  недоумение:  "А что такое
LOOP?"  Ответ прост. Дело в том, что когда
Вы пишете программу в каком-либо Ассембле-
ре, то он предоставляет для удобства такое
понятие, как "метка". Все ссылки аресуются
на неё, а не на реальный адрес, что весьма
облегчает  написание  и отладку программы.
Ведь  слово  запомнить гораздо проще, чем,
например,  "#7A3E". Да и при необходимости
добавить строку-другую в уже готовую прог-
рамму вам не придётся самому пересчитывать
все адреса - это произойдёт автоматически.
  Должен  заметить,  что  такого фрагмента
программы,  как  этот,  вы  почти нигде не
встретите. Сочетание команд

            DEC  B: JR NZ,LOOP

почти всегда заменяют одной командой

                  DJNZ,

читающейся,  как  "уменьшить  В и перейти,
если  не ноль". Эта команда - двухбайтная,
и поэтому её использование даёт некоторую
экономию памяти. Опять-таки, из-за неё ре-
гистр  В обычно используют для организации
счётчиков. Имеет она и недостаток: считать
можно  только до 256, но это можно обойти,
использовав вложенность.
  А  теперь  перепишем  нашу  программу  с
учётом всего вышеизоженного:

         LD   B,5
 LOOP    ........
           тело
           цикла
         ........
         DJNZ LOOP

          Продолжение следует...

             ──═══════════──





Другие статьи номера:

ZX-Обоз - Обзор электронной прессы: ZX-News 47, Don News 7, Buzz 17.

Ликбез - Ассемблер взгляд издалека: Команды единичного приращения, прямой и относительный переход, организация цикла.

Лит. страничка - Гриф "Y-II" (Дневник - продолжение).

Обратная связь - Пару слов об Оптроне 27. К вопросу о прикладном применении Спектрума.

Реклама - Реклама и объявления...

Рубрика X - О Львовском базаре.

Четыре килобайта - 200-й юбилей А.С.Пушкина.


Темы: Игры, Программное обеспечение, Пресса, Аппаратное обеспечение, Сеть, Демосцена, Люди, Программирование

Похожие статьи:
Лит. Страничка - ночная смена (окончание).
мысли - просто разные мысли...
Чернокнижник - Я чернокнижник, я продал свою душу Князю Тьмы!
Сказка - ДЕМОН, RU$$ и "дорога жизни".
Разборочка - Формат отгрузки в игре Bard'S Tale.

В этот день...   21 ноября