Зарегистрировать контент после исполнения - PullRequest
0 голосов
/ 13 июня 2019

Я пытаюсь понять, как работает сборка, но мне очень тяжело. Учебники не помогают, и мне не с кем спросить лично, поэтому я пытаюсь с чего-то начать.
Может кто-нибудь объяснить мне это шаг за шагом, что происходит в этом коде и каков ответ на вопрос ниже?

Каково содержание R16, R17, R18 после выполнения следующих инструкций?

  ldi   r16, 0xab 
  clr   r17 
  ldi   r18, 0x04 
l1:
  inc   r16 
  dec   r18 
  brne  l1 
  sbrc  r16, 2 
  ldi   r17, 33
  nop

Я понимаю, в первой строке мы загружаем шестнадцатеричное значение в регистр 16, затем регистр 17 очищается по какой-то причине, я не знаю почему, затем в третьей строке мы загружаем шестнадцатеричное 04 для того, чтобы зарегистрировать 18, затем «l1:» ​​- это петля правильно? И после этого я не уверен, что происходит. Мы увеличиваем регистр 16, уменьшаем регистр 18, а остальное я не понимаю? Что делают другие строки кода? когда цикл заканчивается?

Пожалуйста, помогите и спасибо заранее!

1 Ответ

2 голосов
/ 28 июня 2019

Если вы не знаете, что делает конкретная инструкция на ассемблере, всегда обращайтесь к Руководству по набору инструкций AVR , где все инструкции подробно описаны.

Инструкция brneусловная ветвь («BRanch, если не равно»).

brne l1 говорит: «Если не равно, перейдите к метке« l1 », иначе продолжите со следующей инструкцией«

Не равно?Что должно быть «не равно» чему?

Здесь вступает в игру основа многих процессоров и языков ассемблера:

«Регистр состояния»

Вв так называемом «регистре состояния» (SREG) есть несколько флагов (одиночных битов), некоторые из них автоматически обновляются после завершения арифметической операции.

Инструкция dec rXY уменьшает значение регистразначение и автоматически обновляет «нулевой флаг» регистра состояния, то есть флаг, который просто указывает, привела ли предыдущая арифметическая инструкция к значению 0.

Нормальные сравнения (инструкция cmp rAB, rXY) реализованы в аппаратном вычитания , то есть cmp r1, r2 почти такое же, как sub r1, r2;особенно инструкции обе обновляют флаги состояния, соответствующие результату операции.Единственное различие между этими двумя операциями состоит в том, что sub изменяет значение r1 на результат вычитания, в то время как cmp не изменяет никакой регистр и просто отбрасывает результирующее значение, но все еще обновляет флаги состояния.

Если cmp реализовано как вычитание, можно увидеть, что cmp r1, r1 (оба значения равны) дает результат ноль , устанавливая флаг нуля в 1.Неравные значения приводят к ненулевому результату, т. Е. Нулевой флаг = 0.

Следовательно, brne ... разветвляется, если результат предыдущей операции не приводит к 0.

dec rXY уменьшает значение регистра и устанавливает нулевой флаг в соответствии с результатом, т.е. если после уменьшения регистр содержит 0, устанавливается нулевой флаг (1) и brne ... фактически означает «ветвление, если результат dec равен , а не ноль».

Таким образом, цикл повторяется до тех пор, пока r18 не уменьшится до нуля.

sbrc ... инструкция является мнемосхемой для «Пропустить, если бит в регистре очищен», она приводит к пропуску следующей инструкции или не зависит от значения регистра в бите.Посмотрите это в руководстве по набору инструкций.

...