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

Насколько умна директива EQU в Keil uVision?

Приветствую.

Решил прямо в .asm-файле сделать финт ушами вычислить некое арифметическое выражение с константами.

Имеется startup-файл, в котором определена таблица векторов прерываний

__Vectors       DCD     __initial_sp               ; Top of Stack
                DCD     Reset_Handler              ; Reset Handler
                DCD     NMI_Handler                ; NMI Handler
                DCD     HardFault_Handler          ; Hard Fault Handler
                DCD     MemManage_Handler          ; MPU Fault Handler
                DCD     BusFault_Handler           ; Bus Fault Handler
                DCD     UsageFault_Handler         ; Usage Fault Handler
                DCD     0                          ; Reserved
                DCD     0                          ; Reserved
                DCD     0                          ; Reserved
                DCD     0                          ; Reserved
                DCD     SVC_Handler                ; SVCall Handler
                DCD     DebugMon_Handler           ; Debug Monitor Handler
                DCD     0                          ; Reserved
                DCD     PendSV_Handler             ; PendSV Handler
                DCD     SysTick_Handler            ; SysTick Handler

                ; External Interrupts
                ...

 

Значения __initial_sp, Reset_Handler и остальные - константы, их реальные числовые значения становятся известны на этапе линковки.

Хочу определить макрос, делающий очень простые арифметические операции над этими константами, чтобы получить результирующее значение в виде одного числа.

Однако, даже простое суммирование, например

__MY_CALC_ADDR__    EQU    Reset_Handler + NMI_Handler

вызывает ошибку

Цитата

error: A1109E: Bad expression type

 

При этом само выражение (в примере Reset_Handler + NMI_Handler) использовать можно где-угодно, но я хотел заменить его одним именем...

 

Этому есть какое-то логичное объяснение?

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

Конечно есть. Нужно прочитать описание директив компилятора armasm.exe - конкретно EQU.

http://infocenter.arm.com/help/index.jsp?topic=/com.arm.doc.kui0100a/armasm_caccddic.htm

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

Не вижу противоречий. Reset_Handler и прочие - константы.

Например,

__Vectors_Size  EQU  __Vectors_End - __Vectors

считает правильно, но это всего лишь метки (относительные адреса).

 

Мне казалось, что и символами Reset_Handler и пр. можно оперировать как угодно, что (почти) подтверждается правильной работой конструкции

__Vectors       DCD     __initial_sp               ; Top of Stack
                DCD     Reset_Handler              ; Reset Handler
                DCD     NMI_Handler                ; NMI Handler
                DCD     HardFault_Handler          ; Hard Fault Handler
                DCD     MemManage_Handler          ; MPU Fault Handler
                DCD     BusFault_Handler           ; Bus Fault Handler
                DCD     UsageFault_Handler         ; Usage Fault Handler
                DCD     __initial_sp + Reset_Handler + NMI_Handler          ; <- + HardFault_Handler + ...
                DCD     0                          ; Reserved
                DCD     0                          ; Reserved
                DCD     0                          ; Reserved
                DCD     SVC_Handler                ; SVCall Handler
                DCD     DebugMon_Handler           ; Debug Monitor Handler
                DCD     0                          ; Reserved
                DCD     PendSV_Handler             ; PendSV Handler
                DCD     SysTick_Handler            ; SysTick Handler

                ; External Interrupts

 

Мануал говорит, что это как #define в Си, однако если я эту сумму вынесу в EQU и подставлю в DCD символическое имя - будет ошибка.

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

11 часов назад, Arlleex сказал:

Значения __initial_sp, Reset_Handler и остальные - константы, их реальные числовые значения становятся известны на этапе линковки.

Хочу определить макрос, делающий очень простые арифметические операции над этими константами, чтобы получить результирующее значение в виде одного числа.

Если хотя бы один из ISR, на которые ссылается таблица прерываний, определён в другом файле (а не в этом .asm), то указатель на него будет не константой. Он будет браться на этапе компоновки из таблиц экспорта .obj-файлов. А значит на этапе компиляции он неизвестен.

11 часов назад, Arlleex сказал:

Однако, даже простое суммирование, например


__MY_CALC_ADDR__    EQU    Reset_Handler + NMI_Handler

вызывает ошибку

Естественно. Чтобы так сделать надо все вектора из таблицы прерываний направить на метки внутри этого .asm-файла.

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

Присоединяйтесь к обсуждению

Вы можете написать сейчас и зарегистрироваться позже. Если у вас есть аккаунт, авторизуйтесь, чтобы опубликовать от имени своего аккаунта.

Гость
Ответить в этой теме...

×   Вставлено с форматированием.   Вставить как обычный текст

  Разрешено использовать не более 75 эмодзи.

×   Ваша ссылка была автоматически встроена.   Отображать как обычную ссылку

×   Ваш предыдущий контент был восстановлен.   Очистить редактор

×   Вы не можете вставлять изображения напрямую. Загружайте или вставляйте изображения по ссылке.

×
×
  • Создать...