Помощь - Поиск - Пользователи - Календарь
Полная версия этой страницы: Макрос на C содержит asm.
Форум разработчиков электроники ELECTRONIX.ru > Микроконтроллеры (MCs) > Cредства разработки для МК > IAR
Alex ma
Необходимо загрузить константу в Z регистр и косвенно вызвать подпрограмму.
а – константа.

Сам макрос:
#define IcallFunc(a)\
{\
asm ("LDI r30, Low(a)\n LDI r31, High(a)\n ICALL");\
}\

Применение:
IcallFunc (0х0104); по идеи вызывается подпрограмма по адресу 0х0104.

Пишет:
Error[Og005]: Unknown symbol in inline assembly: "a"

Если объявить переменную а,
unsigned int a; тогда
IcallFunc (0х0104), нормально компилируется, но!

17: IcallFunc (0x0104);
+0000008D: EFE7 LDI R30,0xF7 Load immediate
+0000008E: E0F0 LDI R31,0x00 Load immediate
+0000008F: 9509 ICALL Indirect call to (Z)
В место константы 0х0104, загружает в r30, r31 адрес SRAM где расположена переменная а – 0x00F7 SRAM, значение переменной 0x0000.
Как заставить загружать константу 0х0104 а, не адрес SRAM где расположена переменная , мне не понятно.
Сергей Борщ
Цитата(Alex ma @ Dec 24 2006, 12:27) *
Необходимо загрузить константу в Z регистр и косвенно вызвать подпрограмму.
Для этого не нужен inline-asm
Код
     ((void (*)(void))0x104)();

     25              ((void (*)(void))0x104)();
   \   00000000   E0E4               LDI     R30, 4
   \   00000002   E0F1               LDI     R31, 1
   \   00000004   9509               ICALL
Только не забываем, что у IAR адреса байтовые, а в Z надо грузить адрес слова, т.е. байтовый пополам.
А с параметрами inline-asm не работает. Более того, умный оптимизатор глубоко плюет на asm. Например, такой пример:
Код
static void func(uint8_t param)  // параметр должен передаваться в R16, static чтобы заинлайнить
{
     asm("STS     TestCell, R16");
}  

void main()
{
     func(123);
}
Тут оптимизатор видит, что в func памаметр не используется и в main его просто не загружает в r16 перед асм-вставкой. Они так и пишут в доке - инлайн-асм можно сказать что не получился, на него "забили", поэтому пользуйте либо имеющиеся intrinsic -функции, либо пишите всю функцию на асме и прилинковывайте к проекту.
Alex ma
Цитата(Сергей Борщ @ Dec 24 2006, 16:13) *
Цитата(Alex ma @ Dec 24 2006, 12:27) *

Необходимо загрузить константу в Z регистр и косвенно вызвать подпрограмму.
Для этого не нужен inline-asm
Код
     ((void (*)(void))0x104)();

     25              ((void (*)(void))0x104)();
   \   00000000   E0E4               LDI     R30, 4
   \   00000002   E0F1               LDI     R31, 1
   \   00000004   9509               ICALL
Только не забываем, что у IAR адреса байтовые, а в Z надо грузить адрес слова, т.е. байтовый пополам.
А с параметрами inline-asm не работает. Более того, умный оптимизатор глубоко плюет на asm. Например, такой пример:
Код
static void func(uint8_t param)  // параметр должен передаваться в R16, static чтобы заинлайнить
{
     asm("STS     TestCell, R16");
}  

void main()
{
     func(123);
}
Тут оптимизатор видит, что в func памаметр не используется и в main его просто не загружает в r16 перед асм-вставкой. Они так и пишут в доке - инлайн-асм можно сказать что не получился, на него "забили", поэтому пользуйте либо имеющиеся intrinsic -функции, либо пишите всю функцию на асме и прилинковывайте к проекту.


Спасибо, на Си лучше. Сам только додумался до asm
Для просмотра полной версии этой страницы, пожалуйста, пройдите по ссылке.
Invision Power Board © 2001-2025 Invision Power Services, Inc.