mbed操作系统移植到TivaC TM4123,带来动态中断处理问题
最近,我试图将mbed操作系统移植到Tiva-C launchpad TM4C123,但mbed提供的文件cmsis_nvic.C和cmsis_nvic.h存在问题mbed操作系统移植到TivaC TM4123,带来动态中断处理问题,c,arm,cortex-m,texas-instruments,mbed,C,Arm,Cortex M,Texas Instruments,Mbed,最近,我试图将mbed操作系统移植到Tiva-C launchpad TM4C123,但mbed提供的文件cmsis_nvic.C和cmsis_nvic.h存在问题 #ifndef MBED_CMSIS_NVIC_H #define MBED_CMSIS_NVIC_H #define NVIC_NUM_VECTORS (154) // CORE + MCU Peripherals #define NVIC_USER_IRQ_OFFSET 16 #include "c
#ifndef MBED_CMSIS_NVIC_H
#define MBED_CMSIS_NVIC_H
#define NVIC_NUM_VECTORS (154) // CORE + MCU Peripherals
#define NVIC_USER_IRQ_OFFSET 16
#include "cmsis.h"
#ifdef __cplusplus
extern "C" {
#endif
void NVIC_SetVector(IRQn_Type IRQn, uint32_t vector);
uint32_t NVIC_GetVector(IRQn_Type IRQn);
#ifdef __cplusplus
}
#endif
#endif
这个模块应该动态地将OS定时器的中断处理程序分配给可寻址函数(或者据我所知)
发生的情况是,软件在执行以下行后跳转到“硬故障处理程序”
vectors[i] = old_vectors[i];
这是我使用的文件
#include "cmsis_nvic.h"
#define NVIC_RAM_VECTOR_ADDRESS (0x02000000) // Vectors positioned at start of RAM
#define NVIC_FLASH_VECTOR_ADDRESS (0x0) // Initial vector position in flash
void NVIC_SetVector(IRQn_Type IRQn, uint32_t vector) {
uint32_t *vectors = (uint32_t*)SCB->VTOR;
uint32_t i;
// Copy and switch to dynamic vectors if the first time called
if (SCB->VTOR == NVIC_FLASH_VECTOR_ADDRESS) {
uint32_t *old_vectors = vectors;
vectors = (uint32_t*)NVIC_RAM_VECTOR_ADDRESS;
for (i=0; i<NVIC_NUM_VECTORS; i++) {
vectors[i] = old_vectors[i];
}
SCB->VTOR = (uint32_t)NVIC_RAM_VECTOR_ADDRESS;
}
vectors[IRQn + 16] = vector;
}
uint32_t NVIC_GetVector(IRQn_Type IRQn) {
uint32_t *vectors = (uint32_t*)SCB->VTOR;
return vectors[IRQn + 16];
}
我正在打电话
NVIC_设置向量(IRQn_类型IRQn,uint32_t向量)
从文件us_ticker.c中,如下所示
NVIC设置向量(TIMER0A\u IRQn,(uint32\u t)us\u ticker\u irq\u handler)
(我的编译器是ARM GCC,我使用CDT进行构建,使用GDB openOCD进行调试,并在Eclipse上集成了所有这些工具)
有人能告诉我这里出了什么问题吗?或者至少我应该在哪里调试或阅读以帮助我解决此问题??
更新
我解决了部分问题,向量没有指向目标SRAM的第一个地址,而目标SRAM应该是
#define NVIC_RAM_VECTOR_ADDRESS (0x20000000)
而不是
#define NVIC_RAM_VECTOR_ADDRESS (0x02000000)
现在,当调用NVIC_SetVector时,函数被执行。但是当启用中断时,软件仍然跳转到硬故障,我猜(只是猜测或可能是解决方案的一部分)头文件中的定义没有正确配置,有人能向我解释一下它们是什么意思吗?如何计算向量地址的数量?用户偏移量是多少?我已经解决了这个问题,下面是我的发现 1-
NVIC\u RAM\u VECTOR\u ADDRESS
不是我的目标RAM的第一个地址,应该是“0x20000000”
2-应更新链接器文件,以便堆栈指针不应写入新复制的向量表。所以,将RAM地址移动向量表应该占用的字节数
3-(主要原因)在函数
NVIC\u SetVector
中,i
被声明为uint32\u t
,然后与小于255的预处理器值进行比较。因此,通过将uint32\u t
与uint8\u t
进行比较,将UL
添加到预处理器值,它解决了整个问题。我已经解决了这个问题,以下是我的发现
1-NVIC\u RAM\u VECTOR\u ADDRESS
不是我的目标RAM的第一个地址,应该是“0x20000000”
2-应更新链接器文件,以便堆栈指针不应写入新复制的向量表。所以,将RAM地址移动向量表应该占用的字节数
3-(主要原因)在函数
NVIC\u SetVector
中,i
被声明为uint32\u t
,然后与小于255的预处理器值进行比较。因此,通过将uint32\u t
与uint8\u t
进行比较,将UL
添加到预处理器值中,解决了整个问题。i的值是多少?也就是说,如果>0,则一些设置为ok。如果不是,则使用gdb打印值。您正在硬连线16
——这是NVIC\u用户\u IRQ\u偏移量
?如果是,就用它。您是否能跑过终点(例如,i
=NVIC\u NUM\u VECTORS
)。你能用gdb戳向量吗?VTOR
在开始时有效吗?(即,是两个正确值之一:0/0x2000000)。它是提取旧的向量还是存储问题的向量(即dox=old\u vectors[i];vectors[i]=x;
并查看哪条线路出现故障)?我希望您正在进行-O0
调试。您是否需要对任何指针变量执行volatile
?我已经更新了问题?您能检查一下并告诉我您是否有答案吗?TIMER0A\u IRQn
的定义是什么?它是矢量号,还是代码期望的中断号(矢量号减16)?另见数据表中的表2-9;您有超过66个外围IRQ…TIMER0A\u IRQn
是中断号(CMSIS Complient driver),您是对的,我已将NVIC\u NUM\u VECTORS
的值更新为154。现在,软件没有跳转到硬故障,但仍然无法正常工作,因为它仍然指向原始中断向量确保链接器脚本不会将数据放置在您希望定位RAM向量的位置,否则您可能会在您想要的数据(可能是堆栈空间)上复制向量表,同样,向量表可能会被其他数据覆盖。i
的值是多少?也就是说,如果>0,则一些设置为ok。如果不是,则使用gdb打印值。您正在硬连线16
——这是NVIC\u用户\u IRQ\u偏移量
?如果是,就用它。您是否能跑过终点(例如,i
=NVIC\u NUM\u VECTORS
)。你能用gdb戳向量吗?VTOR
在开始时有效吗?(即,是两个正确值之一:0/0x2000000)。它是提取旧的向量还是存储问题的向量(即dox=old\u vectors[i];vectors[i]=x;
并查看哪条线路出现故障)?我希望您正在进行-O0
调试。您是否需要对任何指针变量执行volatile
?我已经更新了问题?您能检查一下并告诉我您是否有答案吗?TIMER0A\u IRQn
的定义是什么?它是矢量号,还是代码期望的中断号(矢量号减16)?另见数据表中的表2-9;您有超过66个外围IRQ…TIMER0A\u IRQn
是中断号(CMSIS Complient driver),您是对的,我已将NVIC\u NUM\u VECTORS
的值更新为154。现在,软件没有跳转到硬故障,但仍然无法正常工作,因为它仍然指向原始中断向量确保链接器脚本不会将数据放置在您希望定位RAM向量的位置,否则您可能正在复制