Перейти к содержанию

DSP-инструкции Armv7E-M

Цифровой фильтр — это в основном умножения с накоплением: отсчёт на коэффициент, плюс к сумме. У Cortex-M4 есть команды, которые делают два таких умножения 16 × 16 бит за раз и складывают байты и полуслова параллельно. Это DSP-расширение архитектуры Armv7-M.

Обновлено Редакция GAW

DSP-инструкции — команды необязательного DSP-расширения архитектуры Armv7-M. Реализация архитектуры с этим расширением называется Armv7E-M; такие команды есть, например, у ядра Cortex-M4. Расширение добавляет к набору Thumb-2 команды с насыщением, умножения 16 × 16 бит с накоплением и SIMD-команды, которые обрабатывают сразу два полуслова или четыре байта одного регистра (Armv7-M ARM, разд. A1.3). Arm в руководстве по Cortex-M4 перечисляет их среди главных возможностей ядра: однотактные и SIMD-умножения с накоплением и арифметика с насыщением (DUI 0553B, разд. 1.1); у Cortex-M3 в списке команд их нет, из команд насыщения там только SSAT и USAT (DUI 0552A, разд. 3.1 и 3.7).

Группы команд

ГруппаПримерыЧто делает
Умножение с накоплениемSMLAD, SMLALD, SMLABBSMLAD: 32 = 32 + 16 × 16 + 16 × 16; SMLALD: то же с 64-битным аккумулятором; SMLABB: одно произведение 16 × 16 плюс 32-битный аккумулятор (A7.7.136, A7.7.137, A7.7.140)
Умножение слова на полусловоSMLAWB, SMULWBстаршие 32 бита произведения 32 × 16
Параллельное сложениеSADD16, UADD8, QADD16два полуслова или четыре байта сразу
НасыщениеQADD, QSUB, SSAT16результат не переходит через границу диапазона
УпаковкаPKHBT, SXTB16сборка и расширение полуслов и байтов

По табл. A4-6 — A4-14 Armv7-M ARM. Параллельные команды собраны из префикса и операции: префиксы S и U — знаковая и беззнаковая арифметика по модулю, Q и UQ — с насыщением, SH и UH — с делением результата пополам; операции — ADD16, SUB16, ASX, SAX, ADD8, SUB8. Всего 36 сочетаний. SIMD-команды пишут во флаги GE[3:0] результат по каждой части, и команда SEL по этим флагам собирает итог из байтов двух регистров.

SMLAD и фильтры

SMLAD берёт два регистра как пары 16-битных знаковых чисел, перемножает младшие половины и старшие половины и прибавляет оба произведения к 32-битному аккумулятору. Умножения переполниться не могут, а если переполнится сложение, ставится флаг Q (разд. A7.7.137). Если отсчёты и коэффициенты КИХ-фильтра хранятся в формате Q15 парами в 32-битных словах, одна команда SMLAD считает два отвода фильтра (наш вывод из определения команды). Отсюда выигрыш Cortex-M4 в обработке звука и сигналов датчиков по сравнению с Cortex-M3, которому на те же два отвода нужны отдельные умножения и сложения.

Как использовать

На C эти команды вызывают через встроенные функции CMSIS: __SMLAD(), __SADD16(), __QADD() и другие. В заголовке cmsis_gcc.h они определены только при __ARM_FEATURE_DSP == 1 — компилятор задаёт этот макрос для ядер с DSP-расширением, поэтому на Cortex-M3 такой код не соберётся. Базовые команды насыщения SSAT и USAT есть и без расширения — о них в термине «Арифметика с насыщением». Числа с плавающей точкой DSP-расширение не обрабатывает: это работа отдельного FPU.

Частые вопросы

Есть ли DSP-инструкции у Cortex-M3?

Нет. DSP-расширение необязательное, реализация архитектуры с ним называется Armv7E-M (Armv7-M ARM, разд. A1.3). В сводной таблице команд Cortex-M3 нет ни SMLAD, ни QADD, ни SIMD-сложений, а из команд насыщения есть только базовые SSAT и USAT (DUI 0552A, разд. 3.1 и 3.7); у Cortex-M4 весь набор есть (DUI 0553B). В CMSIS функции вроде __SMLAD определены лишь при __ARM_FEATURE_DSP == 1, так что на Cortex-M3 код с ними просто не соберётся.

Что делает команда SMLAD?

Берёт два 32-битных регистра как пары 16-битных знаковых чисел, перемножает младшие половины между собой и старшие между собой и прибавляет обе суммы к 32-битному аккумулятору — одной командой. Вариант SMLADX перед этим меняет местами половины второго операнда. Если сумма переполняет 32 бита, ставится флаг Q (Armv7-M ARM, разд. A7.7.137).

Нужно ли писать на ассемблере, чтобы использовать DSP-инструкции?

Нет. Заголовки CMSIS-Core дают встроенные функции __SMLAD, __SADD16, __QADD и другие: каждая разворачивается в одну команду ядра. Определены они только для ядер с DSP-расширением — при __ARM_FEATURE_DSP == 1 (cmsis_gcc.h), поэтому код с ними сразу показывает, что ему нужно ядро Armv7E-M.

Источники

  1. Arm. Armv7-M Architecture Reference Manual (ARM DDI 0403E.e, ID021621) — разд. A1.3: необязательное DSP-расширение добавляет в набор Thumb команды цифровой обработки сигналов, в том числе с насыщением и беззнаковые SIMD; реализация с ним называется Armv7E-M; разд. A2.3.2: флаг Q ставят SSAT, USAT и некоторые умножения DSP-расширения, флаги GE[3:0] (бит 19:16, только с DSP) — результаты по байтам и полусловам SIMD, их использует SEL; разд. A4.4.3, табл. A4-6 и A4-8: SMLABB… (32 = 32 + 16 × 16), SMLAD (32 = 32 + 16 × 16 + 16 × 16), SMLALD (64 = 64 + 16 × 16 + 16 × 16), SMLAWB (32 = 32 + 32 × 16), SMMLA, SMUAD, SMUSD, UMAAL (64 = 32 + 32 + 32 × 32); разд. A4.4.4, табл. A4-10, A4-11: SSAT16, USAT16, QADD, QSUB, QDADD, QDSUB; разд. A4.4.7, табл. A4-14: префиксы S, Q, SH, U, UQ, UH и операции ADD16, ASX, SAX, SUB16, ADD8, SUB8 — 36 сочетаний; разд. A7.7.137: SMLAD выполняет два знаковых умножения 16 × 16 и прибавляет их к 32-битному аккумулятору, X меняет полуслова второго операнда, при переполнении сложения ставит Q, умножения переполниться не могут
  2. Arm. CMSIS-Core cmsis_gcc.h, V5.4.1, 27 May 2021 (Apache-2.0) — функции __SADD16, __SMLAD, __SMLADX, __QADD и другие определены только при __ARM_FEATURE_DSP == 1; __SSAT и __USAT — команды для Armv7-M, Armv7E-M и Armv8-M Mainline, для остальных ядер — программная замена на C
  3. Arm. Cortex-M4 Devices Generic User Guide (ARM DUI 0553B, ID012616) — разд. 1.1: ядро с трёхступенчатым конвейером, необязательный FPU одинарной точности по IEEE 754, однотактные и SIMD-умножения и умножения с накоплением, арифметика с насыщением, аппаратное деление; бит 27 Q — флаг переполнения и насыщения DSP; разд. 3.6.4: SMLAD и SMLADX рассматривают операнды как четыре 16-битных полуслова; разд. 3.7: команды насыщения, в том числе QADD, QSUB, QDADD, QDSUB и SIMD-варианты
  4. Arm. Cortex-M3 Devices Generic User Guide (ARM DUI 0552A) — разд. 3.1, табл. 3-1 — сводка команд Cortex-M3: команд SMLAD, QADD, SADD16 нет; разд. 3.7: команды насыщения — только SSAT и USAT

Нашли ошибку?