Разработка устройств на основе цифровых сигнальных процессоров фирмы Analog Devices с использованием Visual DSP++ - Олег Вальпа
Шрифт:
Интервал:
Закладка:
Режим блокировки переполнения ALU разрешается при установке в единицу бита 2 регистра MSTAT. В этом режиме при переполнении ALU разряд AV устанавливается в единицу и при последующих операциях остается в этом состоянии. Таким образом, последующее переполнения уже не генерируются. Бит состояния AV можно очистить непосредственно с DMD шины путем записи в регистр состояния ASTAT нуля.
Арифметико-логическое устройство поддерживает операции деления. Деление осуществляется путем сложения и циклического сдвига чисел с помощью двух специальных примитивов деления DIVS и DIVQ. Команда DIVS вычисляет знаковый бит частного, а DIVQ вычисляет один бит частного. Данные команды применяются для деления знаковых или беззнаковых чисел. Алгоритм деления выполняет либо сложение, либо вычитание, основываясь на знаках делителя и частичного остатка. Остаток при этих операциях недоступен. При этом делитель и делимое должны быть одного типа. Обычная точность деления для 32-разрядного делимого, 16-разрядного делителя и 16-разрядного остатка реализуется за 16 циклов. Делитель может быть сохранен в регистре AX0, АХ1 или в любом регистре результатов R. Старший байт знакового делителя должен находиться либо в регистре AY1, либо в AF, а беззнакового делителя — в регистре AF. Младший байт делителя любого типа должен находиться в AY0. Остаток после деления будет записан в регистр AY0.
Первый из двух примитивов — это команда DIVS (деление-знак). Она предназначена для деления чисел со знаком. Структура операции DIVS показана на рис. 14.3.
Рис. 14.3. Структура операции DIVS
Данная операция вычисляет знаковый бит остатка, выполняя операцию «ИСКЛЮЧАЮЩЕЕ ИЛИ» для знаковых разрядов делителя и делимого.
Регистр AY0 сдвигается на одну позицию таким образом, чтобы знаковый разряд переместился в позицию LSB. Вычисленный знаковый разряд сохраняется в бит AQ регистра состояния. При делении чисел без знака операция DIVS не применяется. В этом случае бит AQ устанавливается в 0. Он показывает, что остаток должен быть положительным.
Второй примитив деления — это команда DIVQ (деление-частное), которая выполняется многократно и генерирует по одному биту частного после очередного выполнения. При простой точности деления чисел без знака команда DIVQ выполняется 16 раз, для такой же точности деления чисел со знаком операция выполняется 15 раз после вычисления знакового разряда с помощью команды DIVS. Операция DIVQ проиллюстрирована на рис. 14.4. DIVQ сдвигает регистр AY0 влево на один разряд так, чтобы новый бит частного оказался в позиции младшего разряда (LSB). Состояние бита AQ, которое генерируется предыдущей операцией, определяет операцию ALU для вычисления частичного результата. Если AQ=1, то ALU добавляет делитель к частичному результату в AF. Если AQ=0, то ALU вычитает делитель из частичного результата в AF. Так же как и в операции DIVS, ALU выводит результат в регистр AF. Формат результата при любом числовом представлении определяется форматом делителя и делимого.
Рис. 14.4. Операция DIVQ
Пусть NL — число разрядов влево и NR — число разрядов вправо от двоичной точки делимого, DL и DR — соответственно то же самое, только для делителя. Тогда частное состоит из NL-DL+1 битов слева от двоичной точки и содержит NR-DR-1 битов справа. Ниже показан пример формата чисел при выполнении операции деления.
Делимое: XXXXX.XXXXXXXXXXXXXXXXXXXXXXXXXXXX
NL=5 бит NR=27 бит
Делитель: XX.XXXXXXXXXXXXXX
DL=2 бит DR=14 бит
Частное: XXXX.XXXXXXXXXXXX
(NL-DL+1)=4 бит (NR-DR-1)=12 бит
Иногда необходимо некоторое изменение формата делимого и делителя. Например, если оба операнда знаковые и дробные (делимое в формате 1.31, а делитель в формате 1.15), то результат запишется в формате 1.15. Таким образом, для получения правильного результата операции деления необходимо, чтобы делимое было меньше делителя.
Чтобы разделить два целых числа (делимое в формате 32, а делитель в формате 16), необходимо перед делением привести делимое к формату 31, т.е. сдвинуть его влево на один разряд. Если результат не может быть представлен в формате частного, как сказано выше, или когда делитель равен нулю или меньше делимого по абсолютному значению, происходит переполнение.
При реализации алгоритма деления для знаковых операндов делитель должен храниться в AX0 и AX1 или в любом регистре с шины R. Старшее слово делимого может быть загружено в AY1 или AF, и младшее слово делимого загружается в AY0. Чтобы вычислить частное, сначала выполняется команда DIVS, которая вычисляет знак частного, за которой следуют 15 команд DIVQ, для вычисления 15 бит частного. Пример подпрограммы знакового деления с фиксированной точкой показан ниже. Эта подпрограмма берет делитель из регистра AX0, старшее слово делимого из AF и младшее слово делимого из AY0. Частное возвращается в AY0.
.MODULE Sig_Div_FP; {
Входные данные:
AF = старшее слово делимого
AY0 = младшее слово делимого
AX0 = 16-битный делитель
Выходные данные:
AY0 = 16-битный результат
Изменяемые регистры:
AY0, AF
Время вычисления=17 циклов
}
.ENTRY sdivfp;
sdivfp: DIVS AF, AX0; {Вычисление знакового бита}
DIVQ AX0; DIVQ AX0; DIVQ AX0; {Вычисление 15 бит частного}
DIVQ AX0; DIVQ AX0; DIVQ AX0;
DIVQ AX0; DIVQ AX0; DIVQ AX0;
DIVQ AX0; DIVQ AX0; DIVQ AX0;
DIVQ AX0; DIVQ AX0; DIVQ AX0;
RTS;
.ENDMOD;
Ниже приводится полный список команд ALU в соответствии с принятыми ранее условными сокращениями. Назначение команд очевидно из их записи и комментариев для некоторых из команд. Команды сложения и сложения с переносом:
[IF cond] |AR| = xop + |yop |;
|AF| |C |
|yop + C |
|constant|
Команды вычитания и вычитания с займом:
[IF cond] |AR| = xop - |yop |;
|AF| |yop+С-1 |
|constant|
[IF cond] |AR| = yop - |xop |;
|AF| |xop+C-1 |
|constant|
Команды логических операций И, ИЛИ, ИСКЛЮЧАЮЩЕЕ ИЛИ:
[IF cond] |AR| = xop |AND| yop;
|AF| |OR |
|XOR|
Команды передачи:
[IF cond] |AR| = PASS|xop |;
|AF| |yop |
|constant|
Команды смены знака:
[IF cond] |AR| = - |xop|;
|AF| |yop|
Команды логического отрицания HE:
[IF cond] |AR| = NOT |xop|;
|AF| |yop|
|0 |
Команды вычисления абсолютного значения:
[IF cond] |AR| = ABS |xop|;
|AF|
Команды инкремента:
[IF cond] |AR| = |yop+1|;
|AF|
Команды декремента:
[IF cond] |AR| = |yop-1|;
|AF|
Команды битовых операций:
[IF cond] |AR| = |TSTBIT n xop|; {операция логического «И» разряда n с 1}
|SETBIT n xop|; {операция установки разряда n в 1}
|CLBIT n xop|; {операция установки разряда n в 0}
|TGBIT n xop|; {операция «ИСКЛЮЧАЮЩЕЕ ИЛИ» бита n с 1}
Здесь n могут принимать значения от 0 до 15
Команды поразрядного деления:
[IF cond] |AR| = DIVS yop, xop;
[IF cond] |AR| = DIVQ xop;
Команды тестирования результата:
NONE = <ALU>;
Последняя команда выполняет заданную команду АЛУ, устанавливает флаги и сбрасывает значение результата. Она позволяет тестировать значения в регистрах без изменения содержимого AR или AF. Строка <ALU> — это любая безусловная команда АЛУ, кроме DIVS, DIVQ и дополнительных команд АЛУ с константами.
Для всех приведенных выше команд ALU разрешено использовать следующие операнды:
xop: AX0, АХ1, AR, MR0, MR1, MR2, SR0, SR1; yop: AY0, AY1, AF;
constant: 0, 1, 2, 4, 8, 16, 32, 64, 128, 256, 512, 1024, 2048, 4096, 8192, 16384, 32767, -2, -3, -5, -9, -17, -33, -65, -129, -257, -513, -1025, -2049, -4097, -8193, -16385, -32768.
Команда DIVS не может использовать регистр AY0 как оператор yop. Коды условия IF соответствуют кодам, приведенным ранее в табличном виде.
Примеры записи команд:
AR=AX0+AY0+C; /* Присвоить регистру AR значение суммы регистров AX0, AY0
и переноса*/
IF EQ AR=AX0+AY0+C; /* Выполнение описанной выше операции при условии
равенства нулю предыдущего результата */
AF=TSTBIT 7 AX; /* Занести в регистр AF значение результата операции
логического «И» разряда 7 с единицей */
Глава 15. Устройство MAC
В этой главе говорится о вычислительном устройстве MAC (умножителя с накопителем) сигнального процессора и выполняемых в нем командах.
Структура устройства MACСвое название устройство MAC получило от сокращения английских слов: multiplier (умножитель) и accumulator (накопитель). Устройство MAC выполняет быстрые одноцикловые операции умножения, умножения с добавлением, умножения с вычитанием, функции насыщения и очистку результата. Функция обратной связи позволяет части результата в одном цикле быть одним из сомножителей в следующем цикле.