我正在研究STM32的启动文件,一时看不懂。中断和异常向量位于 ROM 的开头。有一个 AREA 指令,它有两个参数 CODE 和 DATA。书上说DATA参数对应RAM内存,程序内存的CODE对应FLASH。问题是为什么向量的声明是在数据存储器中完成的,即 内存?我附上清单。部分 - AREA RESET, DATA, READONLY 特别不清楚。毕竟,它应该是 CODE,而不是 DATA。提前致谢。
; Программый модуль стартового файла StartUp_1
; Определить переменную "Размер стека" (1 К байт)
Stack_Size EQU 0x00000400
; Объявить секцию данных для размещения стека системы
; без инициализации памяти, с атрибутом выравнивания
; по 8 байтам
AREA STACK, NOINIT, READWRITE, ALIGN=3
; Зарезервировать область памяти под стек
; с числом байт Stack_Size
Stack_Mem SPACE Stack_Size ; (1 К байт)
; Метка вершины стека (авто-декрементный стек)
__initial_sp
; Vector Table
; Объявить секцию для размещения таблицы векторов
; прерываний/исключений
; Для компановщика определяется как область памяти
; данных RESET. Будет автоматически размещена компоновщиком
; в начале памяти программ
AREA RESET, DATA, READONLY
; Объявить параметры таблицы векторов - глобальными именами
EXPORT __Vectors
EXPORT __Vectors_End
EXPORT __Vectors_Size
; Инициализация векторов обработчиков
; прерываний/исключений
__Vectors DCD __initial_sp ; Вершина стека - Top of Stack
DCD Reset_Handler ; Точка выхода в обработчик исключения
; по сбросу процессора Reset Handler
DCD NMI_Handler ; Точка входа в обработчик
; немаскируемого прерывания NMI
; ...
; Далее по аналогии могут быть объявлены и остальные
; вектора обработчиков прерываний/исключений
__Vectors_End
__Vectors_Size EQU __Vectors_End - __Vectors
; Объявление кодовой секции для размещения
; подпрограмм обработчиков прерываний/исключений
在STM32中,向量不仅可以放在flash中,还可以放在RAM中,同时还可以为它们指定地址。建议大家阅读STM32中断向量传输的答案 好了,然后按照项目的要求设置好一切。例如,在引导加载程序中,将向量放置在 RAM 或闪存中的程序开头地址是合乎逻辑的。最重要的是,将控制器指向SCB->VTOR 寄存器中的向量地址,该地址对应于编译器放置向量的地址。
顺便问一下,这么奇怪的启动文件是从哪里来的?STM32外设库的文件中没有合适的吗?
您从哪里得知向量表在 RAM 中?毕竟,定义因素是READONLY属性(只读),这意味着这是FLASH区域。而READWRITE(读/写)属性对应SRAM。而且文件一点都不奇怪,从ST的原件开始也是一样的。只有在原版中没有俄语注释,并且声明了一堆 HEAP(显然为了简化而省略了,因为我理解战斗训练文件:))。而且中断和异常向量确实位于0x08000000——栈顶,0x08000001——入口点(reset_handler),然后剩下的中断都去了。(0x08000000 FLASH的起始地址)
理论:将程序分成单独的部分允许使用特殊指令 - AREA。它具有以下语法:AREA Section_Name {,type} {, attr} ...,其中:
section_name - 部分名称。类型 — 部分类型。对于包含数据的部分,您必须指定 DATA 类型,对于包含命令的部分,您必须指定 CODE 类型。attr - 附加属性。例如,readonly 或 readwrite 属性指示该段应放置在哪个内存中,align=0..31 属性指定该段应如何在内存中对齐,noinit 属性用于分配不需要的内存区域初始化或初始化为零(使用该属性时,不需要指定节类型,因为它只能用于数据节)。最好借鉴:http ://www.keil.com/support/man/docs/armasm/default.htm
如上所述,向量表确实可以转移到不同的地址(FLASH甚至SRAM),但这是完全不同的话题。
PS:这里是ST startup_stm32f10x_hd.s文件的开头(这里只有代码,没有初始注释):