Знаковые целые числа

Знаковые целые числа

Данная глава посвящена программированию арифметических операций над знаковыми числами, представленными в дополнительном коде (подробней о знаковых числах смотри в приложении Б). Не прибегая к знаковым числам, тяжело решить многие задачи управления. При формировании выходного воздействия любой регулятор либо следящая система опирается на сигнал ошибки, который может изменяться как по величине, так и по знаку. Отрицательные числа могут возникнуть также в результате различных вычислительных операций. И, наконец, числа в дополнительном коде дают возможность использовать действие сложения как альтернативу вычитанию или, если это удобно, наоборот – вместо сложения пользоваться одним только вычитанием.

Особенности работы со знаковыми числами

Система команд AVR изначально оптимизирована для работы со знаковыми числами, а в регистре состояния SREG имеются три специально предназначенных для этих целей флага N, V и S.

Во флаге N хранится знака числа в дополнительном коде. В него копируется содержимое старшего бита результата большинства арифметических и логических операций. Таким образом, N=0 для неотрицательных чисел и N=1 для отрицательных.

Второй бит V из SREG – флаг переполнения в дополнительном коде. В результате действий сложения и вычитания n-разрядных знаковых чисел, в общем случае может быть получен n+1-разрядный результат и флаг V будет установлен, когда произошло переполнение 8-разрядной сетки.

Например, в результате операции сложения двух знаковых чисел

-86 = 0b10101010 и -61 = 0b11000011  (сложение и вычитание знаковых и беззнаковых чисел происходит одинаково) получим следующий результат:

(-86) + (-61) = -147 = 0b101101101 = 0b100000000 + 0b01101101.

Сумма однобайтовых слагаемых вышла за пределы диапазона представления 8-разрядных знаковых чисел -128…+127. В результате переполнения аппаратно будет установлен флаг V.  

Обратите внимание на следующее обстоятельство. Если трактовать те же самые числа, как “правильные” двоичные в позиционной системе исчисления (т.е. 170 = 0b10101010 и 195 = 0b10101010), то в результате их сложения также возникнет переполнение:     

170 + 195 = 365 = 0b101101101 = 0b100000000 + 0b01101101.

Здесь, очевидно, сумма вышла за пределы 0…255 и ее 9-тый бит окажется во флаге переноса С. Однако флаги V и C будут нести в себе совершенно различный смысл. Бит V всегда сигнализирует о переполнении при знаковом сложении (вычитании), в то время, как С – о переполнении беззнаковом.

Так как в дополнительном коде знак размещается в старшем разряде, то определить его можно, только изначально зная разрядность числа. У 8-разрядных чисел он находится во флаге N, у 9-разрядных, которые возникли в результате переполнения, истинный знак надо искать во флаге S. Значение  S получается в результате операции N XOR V. В предыдущем примере S = 0 XOR 1 = 1 (т.е. результат операции сложения отрицательный).

Для изменения знака однобайтовых чисел у AVR имеется инструкция neg Rd (Rd <- 0xFF–Rd+1), которая заменяет собой две команды: com Rd (Rd <- 0xFF–Rd) и inc  Rd (Rd <- Rd+1).

Ту же самую операцию легко можно произвести и над числами с большей разрядностью. В этом случае действия разделяются на две части: сначала число нужно проинвертировать, а затем добавить 1.

Так может выглядеть пример дополнения до двух 16-разрядного числа из регистровой пары R25:R24:

com R24 ;R25:R24 = 0xFFFF – R25:R24 com R25 adiw R24,1 ;R25:R24 = R25:R24 + 1

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


Категория: Микроконтроллеры
Метки:

Написать коментарий

*
= 4 + 6

Добавить изображение

Последние статьи