ARM: как быстро начать писать на ассемблере |
Добавил(а) microsin | ||||
Поначалу ARM довольно непривычный ассемблер (если переучиваться с x86, MCS51 или AVR). Но у него довольно простая и логичная организация, поэтому усваивается быстро. Документации на русском языке по ассемблеру совсем мало, см. [1]. Второе, что хорошо может помочь - это, как ни странно, C-компилятор IAR Embedded Workbench for ARM (далее просто IAR EW ARM). Дело в том, что он со стародавних времен умеет (как и все уважающие себя компиляторы, впрочем) компилировать C-код в код ассемблера, который, в свою очередь, так же легко компилируется ассемблером IAR в объектный код. Поэтому нет ничего лучше написать простейшую функцию на C, скомпилировать её в ассемблер, и сразу станет понятно, какая команда ассемблера что делает, как передаются аргументы и как возвращается результат. Убиваете сразу двух зайцев - обучаетесь ассемблеру и заодно получаете информацию, как интегрировать ассемблерный код в проект на C. Я тренировался на функции подсчета CRC16, и в результате получил её полноценную версию на ассемблере. Вот исходная функция на C (u16 означает unsigned short, u32 - unsigned int, u8 - unsigned char):
Заставить генерировать код ассемблера IAR EW ARM очень легко. В опциях файла crc16.c (добавленного к проекту) поставил галку Override inherited settings, а потом на закладке List поставил 3 галки - Output assembler file, Include source и Include call frame information (хотя последнюю галку, наверное, можно не ставить - она генерит кучу ненужных CFI-директив). После компиляции получился файл папка_проекта \ ewp \ at91sam7x256_sram \ List \ crc16.s. Этот файл также легко можно добавить в проект, как и C-файл (он будет нормально компилироваться). Конечно, когда я подсунул C-компилятору необрезанный вариант C-кода, то он мне выдал такой листинг ассемблера, что я ничего в нем не понял. Но когда выкинул из функции все C-операторы, кроме одного, стало понятнее. Потом шаг за шагом добавлял C-операторы, и вот в итоге что получилось:
Компилятор C от IAR делает на удивление хороший код. Мне совсем мало удалось его оптимизировать. Выкинул только лишний временный регистр, который хотел использовать компилятор (он почему-то взял в качестве лишнего временного регистра LR, хотя R3 и R12 было достаточно), а также убрал пару лишних команд, проверяющих счетчики и выставляющих флаги (просто добавив суффикс S к нужным командам). [Ссылки] 1. Архитектура и система команд RISС-процессоров семейства ARM site:gaw.ru. |