Ревич, Ю.В. Программирование микроконтроллеров AVR: от Arduino к ассемблеру
Глава 7. Система команд АVR 1 79 либо о, либо 1 - сумма двух восьмиразрядных чисел не может превысить число 5 1 0 (255 + 255), именно потому флаг переноса с представляет собой один единственный бит в регистре флагов. Команда brcc (BRanch if Carry Cleared) пред ставляет собой операцию перехода по условию, что флаг переноса равен нулю. Таким образом, если флаг не равен нулю, выполнится операция inc RНl - увели чение значения регистра RНl на единицу, в противном случае это действие будет пропущено. Можно придумать и другие способы программирования этой опера ции. Внимательный читатель, несомненно, уже заметил неточность в программе - а чему равно значение RНl до выполнения нашей процедуры? Вдруг оно совсем не ноль, и тогда нельзя говорить о корректном результате. Поэтому правильней бьmо бы либо дополнить нашу процедуру еще одним оператором, расположив его рань ше всех остальных: clr RНl , либо вместо команды inc применить какой-нибудь из способов загрузки значения 1 в переменную RНl (например, ldi RНl , 1 ) . Заметим, что во всех случаях процедура разрастается по времени - было две команды, стало четыре, причем тут имеется замедление еще и неявного порядка: если все представленные арифметические команды выполняются за один такт, то команда ветвления brcc может выполниться за такт (если с = 1 ) , а может и за два (если с = о) . Итого мы выиграли один регистр, а потеряли два или три такта. И так всегда - как мы уже говорили, есть процедуры, оптимизированные по времени, есть - по числу команд, а могут быть - и по числу занимаемых регистров. Идеа ла, как и везде в жизни, тут не добиться, приходится идти на компромисс. Если вы посмотрите на сводную таблицу команд в руководствах, то можете обра тить внимание, что из восьмибитовых арифметических операций с константой дос тупно только вычитание ( suЬi, sbci ) , напрашивающейся же операции сложения с константой нет. Ограничение легко обходится вычитанием отрицательного числа: команда suЬi ternp, - 1 0 прибавит 10 к ternp, а пара команд: suЬi ternp , Low ( - 500 ) ; sbci ternpl , High ( - 5 0 0 ) - добавит к двухбайтовому числу ternpl : ternp двухбайтовую константу 50 0 . Кроме того, разработчики семейства АVR решили облегчить жизнь пользователям, добавив для двухбайтовых операций с константами в перечень арифметических команд две очень удобные команды: adiw и sЬiw. Единственный их недостаток работают они только со старшими парами регистров, начиная с r2 4-r2 5 . Три последние пары ( r2 6-r2 7 , r2 B-r2 9 и r30-r 3 1 ) носят еще название х, У и z, и мы их будем «проходить» далее в этой главе - они задействованы в операциях обмена данными с памятью, так что операции adiw / sЬiw явно нацелены на манипуляции с адресами в памяти. Но в рассматриваемом случае точно так же работает и пара r2 4-r2 5, которая более нигде вместе не употребляется, и это бывает очень удобно. Независимо от используемой пары, старшим регистром считается тот, что с боль шим номером, а операцию нужно проводить с младшим, при этом перенос учтется автоматически. Например, в результате выполнения последовательности команд: clr r25 ldi r2 4 , 1 00 adiw r24 , 2 0 0
Made with FlippingBook
RkJQdWJsaXNoZXIy MTExODQxMg==