Реклама ⓘ
Главная » Микроконтроллеры
Призовой фонд
на апрель 2024 г.
1. 100 руб.
От пользователей

Реклама ⓘ

Команды передачи управления

Табл 3. Команды передачи управления:

Команда

Описание

Действие

Циклы

Код операции

Флаги

ATtiny

ATmega

rjmp  k

Relative Jump

PC←PC+k+1

2

1100 kkkk kkkk kkkk

None

+

+

ijmp

Indirect Jump to (Z)

PC←(Z)

2

1001 0100 0000 1001

None

±

+

eijmp

Extended Indirect
Jump to (Z)

PC←(EIND:Z)

2

1001 0100 0001 1001

None

-

±

jmp   k

Direct Jump

PC←k

3

1001 010k kkkk 110k
kkkk kkkk kkkk kkkk

None

 -

±

rcall  k

Relative Subroutine Call

STACK←PC+1,
PC←PC+k+1,
SP←SP-2 or 3

3/4

1101 kkkk kkkk kkkk

None

+

+

icall

 

Indirect Call to (Z)

STACK←PC+1, PC←(Z),
SP←SP-2 or 3

3/4

1001 0101 0000 1001

None

±

+

eicall

Extended Indirect
Call to (Z)

STACK←PC+1,
PC←(EIND:Z),
SP←SP-3

4

1001 0101 0001 1001

None

-

±

call  k

Direct Subroutine Call

STACK←PC+1, PC←k,
SP←SP-2 or 3

4/5

1001 010k kkkk 111k
kkkk kkkk kkkk kkkk

None

-

±

ret

Subroutine Return

PC←STACK,
SP←SP+2 or 3

4/5

1001 0101 0000 1000

None

+

+

reti

Interrupt Return

PC←STACK,
SP←SP+2 or 3

4/5

1001 0101 0001 1000

I

+

+

cpse  Rd,Rr 

Compare, Skip if Equal

 

if(Rd=Rr)
PC←PC+2 or 3

1/2/3

0001 00rd dddd rrrr

None

 +   

+

cp   Rd,Rr 

Compare

Rd-Rr 

1

0001 01rd dddd rrrr

Z,C,S,
N,V,H

+

+

cpc   Rd,Rr 

Compare with Carry

Rd-Rr-C 

1

0000 01rd dddd rrrr

Z,C,S,
N,V,H

+

+

cpi   Rd,K  

Compare Register with Immediate

Rd-Rr-K 

1

0011 KKKK dddd KKKK

Z,C,S,
N,V,H

+

+

sbrc  Rr,b 

Skip if Bit in
Register is Cleared

if(Rr(b)=0)
PC←PC+2 or 3

1/2/3

1111 110r rrrr obbb

None

+

+

sbrs  Rr,b 

Skip if Bit in
Register is Set

if(Rr(b)=1)
PC←PC+2 or 3

1/2/3

1111 111r rrrr obbb

None

+

+

sbic  P,b 

Skip if Bit in IO
Register is Cleared

if(P(b)=0)
PC←PC+2 or 3

1/2/3

1001 1001 PPPP Pbbb

None

+

+

sbis  P,b 

Skip if Bit in IO
Register is Set

if(P(b)=1)
PC←PC+2 or 3

1/2/3

1001 1011 PPPP Pbbb

None

+

+

brbc  s,k

Branch if Status
Flag is Cleared

if(SREG(s)=0)
PC←PC+k+1

1/2

1111 01kk kkkk ksss

None

+

+

brbs  s,k

Branch if Status
Flag is Set

if(SREG(s)=1)
PC←PC+k+1

1/2

1111 00kk kkkk ksss

None

+

+

brcc  k

Branch if Carry
Flag is Clearsd

 

if(C=0) PC←PC+k+1

1/2

1111 01kk kkkk k000

None

+

+

brcs  k

Branch if Carry
Flag is Set

if(C=1) PC←PC+k+1

1/2

1111 00kk kkkk k000

None

+

+

brsh   k

Branch if Same
or Higher

 

if(C=0) PC←PC+k+1

1/2

1111 01kk kkkk k000

None

+

+

brlo  k

Branch if Lower

 

if(C=1) PC←PC+k+1

1/2

1111 00kk kkkk k000

None

+

+

brne  k

Branch if Not Equal

 

if(Z=0) PC←PC+k+1

1/2

1111 01kk kkkk k001

None

+

+

breq  k

Branch if Equal

 

if(Z=1) PC←PC+k+1

1/2

1111 00kk kkkk k001

None

+

+

brpl  k

Branch if Plus

 

if(N=0) PC←PC+k+1

1/2

1111 01kk kkkk k010

None

+

+

brmi  k

Branch if Minus

 

if(N=1) PC←PC+k+1

1/2

1111 00kk kkkk k010

None

+

+

brvc  k

Bruach if Overflow
Flag is Cleared

 

if(V=0) PC←PC+k+1

1/2

1111 01kk kkkk k011

None

+

+

brvs  k

Branch if Overflow
Flag is Set

 

if(V=1) PC←PC+k+1

1/2

1111 00kk kkkk k011

None

+

+

brge  k

Branch if Greate or
Equal, Signed

 

if(S=0) PC←PC+k+1

1/2

1111 01kk kkkk k100

None

+

+

brlt  k

Branch if Less than
Zero, Signed

 

if(S=1) PC←PC+k+1

1/2

1111 00kk kkkk k100

None

+

+

brhc  k

Branch if Half Carry
Flag is Cleared

 

if(H=0) PC←PC+k+1

1/2

1111 01kk kkkk k101

None

+

+

brhs  k

Branch if Half Carry
Flag is Set

 

if(H=1) PC←PC+k+1

1/2

1111 00kk kkkk k101

None

+

+

brtc  k

Branch if Transfer
Flag is Cleared

 

if(T=0) PC←PC+k+1

1/2

1111 01kk kkkk k110

None

+

+

brts  k

Branch if Transfer
Flag is Set

 

if(T=1) PC←PC+k+1

1/2

1111 00kk kkkk k110

None

+

+

brid  k

Branch if Interrupt
Disable

 

if(T=0) PC←PC+k+1

1/2

1111 01kk kkkk k111

None

+

+

brie  k

Branch if Interrupt
Enable

 

if(T=1) PC←PC+k+1

1/2

1111 00kk kkkk k111

None

+

+

 

Все команды группы передачи управления приведены в табл.3. Микроконтроллеры AVR могут содержать до 4-х разновидностей команды безусловного перехода. Команды такого типа модифицируют
содержимое программного счётчика, после чего программа продолжает выполняться с нового места (адреса перехода). Безусловный переход в памяти программ происходит не зависимо от каких либо условий, флагов программы и т.д.

Инструкция rjmp k (Относительный безусловный переход) позволяет осуществить переход в диапазоне +2047…-2047 слов в памяти программ от места где она расположена. Адрес перехода при этом зависит от текущего значения программного счётчика и вычисляется как смещение PC+1+k.

Команда ijmp (Косвенный безусловный переход) производит переход в памяти программ в пределах 0…65535 слов по адресу, находящемуся в индексном регистре Z. В этом случае адрес перехода является переменной величиной доступной из программы. Это даёт возможность легко реализовать процедуру ветвления, когда в зависимости от условий должен быть выполнен тот или иной фрагмент кода.

В моделях с объёмом памяти программ 256 кб доступна также команда eijmp (Расширенный безусловный косвенный переход). Она использует 3-байтовый указатель адреса EIND:ZH:ZL. В регистре EIND из пространства РВВ находится 17-тый бит адреса, а переход осуществляется в пределах 0…131071 слов.

Команда jmp k (Абсолютный безусловный переход) - переход по адресу k в любую точку из любого места программы. Абсолютный адрес перехода находится в коде операции, а команда занимает 2 слова (4 байта) и выполняется в течении 3-х машинных циклов.

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

       ldi  ZL,low(label)  ;косвенный переход на метку label
       ldi  ZH,high(label)  
       ijmp
      .
       jmp  label          ;абсолютный переход на метку label
      .
       rjmp label          ;относительный переход на метку label
      .

       .org 0x0200
label:.            ;метка в программе по адресу 0x0200

Другим типом команд являются вызовы подпрограмм. Существуют следующие их разновидности: rcall k (Относительный вызов подпрограммы), icall (Косвенный вызов подпрограммы), eicall (Расширенный косвенный вызов подпрограммы) и call k (Абсолютный вызов подпрограммы). Функционируют такие инструкции аналогично командам безусловного перехода, но с одним существенным отличием. Перед переходом в памяти программ, адрес следующей команды предварительно сохраняется в специально отведённой для этих целей области памяти (стеке). Таким образом, находясь в любой точке программы, сохраняется возможность вернутся в то место, из которого был осуществлен вызов. Это действие осуществляет команда ret (Возврат из подпрограммы). Она загружает в PC сохранённый в стеке адрес возврата, после чего программа продолжает выполняться со следующей команды после rcall k, icall, eicall, call k:

       ldi   ZL,low(func1);косвенный вызов подпрограммы func1
       ldi   ZH,high(func1)  
       icall
      .
       call  func1       ;абсолютный вызов подпрограммы func1
      .
       rcall func1       ;относительный вызов подпрограммы func1
      .

func1:.          ;подпрограмма func1 
       call  func2       ;абсолютный вызов подпрограммы func2
      .
       ret               ;возврат из подпрограммы func1

func2:.          ;подпрограмма func2
       ret               ;возврат из подпрограммы func2

В приведенном примере подпрограмма func1 может вызываться много раз из различных мест программы. Кроме того, в теле самой подпрограммы func1 могут содержаться вызовы различных подпрограмм (вызов func2 и т.д.). Такая организация программы позволяет максимально эффективно использовать ресурсы процессора, делает код более наглядным и позволяет многократно использовать разработанные подпрограммы в дальнейших проектах.

Еще одним скрытым механизмом вызова подпрограмм являются аппаратные прерывания. При их возникновении происходит вызов подпрограммы (обработчика прерывания) по фиксированному адресу (вектору прерывания), при этом адрес возврата также запоминается в стеке. Но в отличии от вызова по командам rcall k, icall, eicall, call k ещё и автоматически сбрасывается флаг глобального разрешения прерываний I в регистре SREG, т.е. запрещаются прерывания во время прерывания. Для выхода из прерывания используется команда reti (Возврат из прерывания) которая, загружает в PC адрес возврата и восстанавливает флаг I (разрешает прерывания при выходе из прерывания):

     .org 0x0002
     rjmp  service_INT0  ;вектор внешнего прерывания INT0

     .org 0x0100
service_ INT0: ̣̣̣̣̣̣̣̣   ;обработчик прерывания INT0  
     reti                 ;возврат в основную программу

Иногда командой reti удобно завершить и обычную подпрограмму. Так бывает, когда, например, при выходе необходимо разрешить прерывания. В этом случае она фактически заменяет собой две инструкции sei (Разрешение прерываний) и ret:

func:  cli       ;глобальный запрет прерываний (I=0)
       .
       reti      ;выход из подпрограммы и разрешение прерываний

Время выполнения rcall k, icall, call k, ret, reti зависит от величины программного счётчика конкретной модели. Если его разрядность более 16 бит (≥ 128 кб FLASH памяти), то для сохранения 3-байтового адреса возврата требуется на один машинный цикл больше.

В данную группу команд включены также 4 инструкции сравнения: cp Rd,Rr (Сравнить регистры), cpс Rd,Rr (Сравнить регистры с учётом переноса), cpi Rd,K (Сравнить регистр c константой), cpse Rd,Rr (Сравнить регистры и пропустить команду если они равны). Строго говоря первые три из них не являются командами передачи управления, так как не могут оказать влияние на счётчик программ. Единственным их предназначением является сравнение числовых величин, находящихся в РОН. Как видно из описания, команда cp Rd,Rr аналогична sub Rd,Rr, вместо cpc Rd,Rr фактически выполняется sbc Rd,Rr, а вместо cpi Rd,K - cubi Rd,K. Разница заключается только лишь в том, что содержимое регистра Rd остаётся неизменным. При этом переопределяется значение флагов Z,C,S, N,V,H регистра SREG по которым и можно судить о соотношении между числовыми величинами. В частности, сравнение двухбайтовых чисел находящихся в регистровых парах R19:R18 R17:R16 можно выполнить следующим образом:

     cp  R18, R16 ; сравнение 2-байтовых чисел       
     cpc R19, R17 ; R19:R18 - R17:R16

В этом примере флага C окажется установленным, когда R19:R18< R17:R16 (сброшенным, когда R19:R18>R17:R16). Что касается флага Z, то в данном случае он не может быть критерием проверки на нуль (Z=1 будет свидетельствовать только о равенстве R19=R17+C).

Стоит заметить также, что, подобно всем остальным командам, использующим непосредственную адресацию, cpi Rd,K может работать только с регистрами  R16…R31.  

Инструкция cpse Rd,Rr выполняется иначе. Она относится к типу Test and Skip (Проверка и пропуск). По логике работы команды такого рода выполняют проверку определённого условия и если оно истинно (в данном случае если Rd=Rr), то следующая в тексте команда пропускается. При этом все флаги программы остаются неизменными.

Помимо этого существуют ещё 4 команды Test and Skip ориентированных на проверку состояния определённого бита в регистрах. Две из них работают с РОН: sbrc Rr,b (Пропуск команды, если бит регистра сброшен), sbrs Rr,b (Пропуск команды, если бит регистра установлен). Ещё две с РВВ: sbic P,b (Пропуск команды, если бит регистра ввода-вывода сброшен), sbis P,b (Пропуск команды, если бит регистра ввода-вывода установлен). Если бит b(0…7) установлен при выполнении команд sbrs Rr,b и sbis P,b или сброшен для sbrc Rr,b, sbic P,b, то производится пропуск следующей команды. Нижеприведённый код демонстрирует программную задержку до тех пор пока не будет нажата кнопка подключённая к линии 1 порта B (пока бит 1 РВВ PINB не будет сброшен):

button_press:
      sbic PINB,1        ; задержка пока на выводе 1 порта B
      rjmp button_press  ; не появится низкий уровень 
     .

В отличии от команд sbrs Rr,b, sbrc Rr,b, которые работают со всеми без исключения РОН, инструкции sbis P,b, sbic P,b могут использовать только первые 32 РВВ. Если учесть, что число управляющих РВВ на много больше то, это довольно существенное ограничение. Конечно те РВВ, доступ к битам которых наиболее важен, разработчики постарались разместить именно в этой области. К ним относятся все регистры управления портами A,B,C,D,E,F, а также ряд других, отвечающих за работу EEPROM, USART, SPI т.д. Во всех остальных случаях необходимо cкопировать содержимое РВВ в один из РОН и уже дальше анализировать состояние соответствующего бита. Программное ожидание сброса бита 2 порта J должно выглядеть следующим образом:

button_press:
      lds R16,PINJ       ; задержка пока на выводе 2 порта J
      sbrc R16,2         ; не появится низкий уровень 
      rjmp button_press
     .

Время выполнения инструкций Test and Skip может быть различным в зависимости от того пропускается следующая команда или нет. В первом случае необходимо 2 машинных цикла, во втором 1. Если же производится пропуск “длинной” команды состоящей из двух слов (lds Rd,k, jmp k и т.д.) на выполнение операции уйдёт 3 цикла.

Флаги программы регистра состояния также не доступны инструкциям sbis P,b, sbic P,b, но из-за важности их значения предусмотрены две команды условного перехода разработанных специально для работы с SREG: brbs s,k (Переход, если бит регистра SREG установлен), brbc s,k (Переход, если бит регистра SREG сброшен). Когда соответствующий бит s в SREG установлен для brbs s,k или сброшен для brbс s,k производится относительный переход в пределах +63…-63 слов (PC+k+1).

Ассемблер AVR поддерживает по 9 различных форм написания инструкций brbs s,k, brbc s,k для разных значений флагов программы (табл.4).

Табл 4. Команды условных переходов по состоянию флагов SREG:

Проверка
флага

Команда условного
перехода

Альтернативная
Форма написания

Условие перехода

C

brbc 0,k

brcc k

Переход если флаг переноса установлен

brsh k

Переход если больше или равно

brbs 0,k

 

brcs k

Переход если флаг переноса сброшен

brlo  k

Переход если меньше

Z

brbc 1,k

breq k

Переход если равно

brbs 1,k

brne k

Переход если не равно

N

brbc 2,k

brpl k

Переход если плюс

brbs 2,k

brmi k

Переход если минус

V

brbc 3,k

brvc k

Переход если флаг дополнительного кода сброшен

brbs 3,k

brvs k

Переход если флаг дополнительного кода установлен

S

brbc 4,k

brge k

Переход если больше или равно нулю (знаковое)

brbs 4,k

brlt k

Переход если меньше нуля (знаковое)

H

brbc 5,k

brhc k

Переход если флаг половинного переноса сброшен

brbs 5,k

brhs k

Переход если флаг половинного переноса установлен

T

brbc 6,k

brtc k

Переход если флаг хранения бита сброшен

brbs 6,k

brts k

Переход если флаг хранения бита установлен

I

brbc 7,k

brid k

Переход если прерывания запрещены

brbs 7,k

brie k

Переход если прерывания разрешены

В ходе программы, как правило, наиболее часто производится проверка флагов Z и C. Если установка флага Z однозначно свидетельствует о нулевом результате операции, то установка флага переноса C может иметь разный смысл в зависимости от того, какая команда оказывает на него влияние.

Следующая подпрограмма осуществляет инкрементирование 4-байтового счётчика R27:R26:R25:R24, а проверка флага C производится с целью установить, происходит ли переполнение младшего слова R25:R24, и если да, то к старшей регистровой паре R27:R26 добавляется 1:

inc_cnt:  
      adiw R24,1   ; добавление 1 к регистровой паре R25:R24
      brcc PC+2    ; и если возникает перенос, то
      adiw R26,1   ; увеличение на 1 регистровой пары R27:R26 
      ret

Другим примером, где необходимо знать состояние флага C, может служить сравнение чисел:

      cpi  R16,0x40 ; сравнить содержимое R16 с числом 0x40 
      brlo ulo      ; перейти наметку ulo если R16 < 0x40
     .
ulo: .

Вместо brcc k, здесь используется более подходящая по смыслу форма написания инструкции brlo k (переход если R16 меньше 0x40).

Подобный понятный символический вид имеют и остальные команды условных относительных переходов: breq k(Переход если равно 0), brne k(Переход если не равно 0), brie k (Переход если прерывания разрешены), brid k (Переход если прерывания запрещены) и т.д.

Перейти к следующей части:

Теги:

Котов Игорь Юрьевич Опубликована: 2012 г. 0 0
Я собрал 0 0
x

Оценить статью

  • Техническая грамотность
  • Актуальность материала
  • Изложение материала
  • Полезность устройства
  • Повторяемость устройства
  • Орфография
0

Средний балл статьи: 0 Проголосовало: 0 чел.

Комментарии (0) | Я собрал (0) | Подписаться

Статью еще никто не комментировал. Вы можете стать первым.
Добавить комментарий
Имя:
E-mail:
не публикуется
Текст:
Защита от спама:
В чем измеряется электрическая мощность?
Файлы:
 
Для выбора нескольких файлов использйте CTRL

Программатор Pickit3
Программатор Pickit3
Катушка Тесла Arduino UNO
вверх