1.使能lcd的硬件驱动后编译报错:
查阅数据手册后发现并没有GPIO-G端口,删掉了|GPIO-G的那一部分后编译通过,lcd正常显示
2.按下五向开关中的sel键后系统直接死机:
实验时,按键采用外部中断方式检测,驱动代码采用rtt的驱动框架:
rt_pin_mode(sel,PIN_MODE_INPUT_PULLUP);
rt_pin_attach_irq(sel, PIN_IRQ_MODE_FALLING, sel_callback, RT_NULL);
rt_pin_irq_enable(sel, PIN_IRQ_ENABLE);
只用了三行就成功开启了按键按下后可以执行相应功能,非常方便......
但是,测试上下左右,sw1,sw2均正常,唯有按下sel后系统直接死机......
sel键对应的io为PD13
查阅后发现其挂在这条线上......
同样在drv_gpio.c文件中发现了:
好家伙,PD13所在的那条线的程序根本没写......
添加如下函数后问题得以解决:
(仿照上面的代码补全这个函数)
void EXTI15_10_IRQHandler(void)
{
GET_INT_SP();
rt_interrupt_enter();
if(EXTI_GetITStatus(EXTI_Line10)!=RESET)
{
HAL_GPIO_EXTI_Callback(GPIO_Pin_10);
EXTI_ClearITPendingBit(EXTI_Line10);
}
if(EXTI_GetITStatus(EXTI_Line11)!=RESET)
{
HAL_GPIO_EXTI_Callback(GPIO_Pin_11);
EXTI_ClearITPendingBit(EXTI_Line11);
if(EXTI_GetITStatus(EXTI_Line12)!=RESET)
{
HAL_GPIO_EXTI_Callback(GPIO_Pin_12);
EXTI_ClearITPendingBit(EXTI_Line12);
}
if(EXTI_GetITStatus(EXTI_Line13)!=RESET)
{
HAL_GPIO_EXTI_Callback(GPIO_Pin_13);
EXTI_ClearITPendingBit(EXTI_Line13);
}
if(EXTI_GetITStatus(EXTI_Line14)!=RESET)
{
HAL_GPIO_EXTI_Callback(GPIO_Pin_14);
EXTI_ClearITPendingBit(EXTI_Line14);
}
if(EXTI_GetITStatus(EXTI_Line15)!=RESET)
{
HAL_GPIO_EXTI_Callback(GPIO_Pin_15);
EXTI_ClearITPendingBit(EXTI_Line15);
}
rt_interrupt_leave();
FREE_INT_SP();
}
3.left和sw2的中断回调函数互相进入:
问题就是这样的:
(我写的测试代码是left的回调函数中打印“left”,sw2的回调函数中打印“sw2 what what”,但是不管先按left还是先按sw2,都会打印上图中信息)
解决这个问题很简单,依照下面的代码更改你的EXTI9_5_IRQHandler函数即可:
void EXTI9_5_IRQHandler(void)
{
GET_INT_SP();
rt_interrupt_enter();
// if( (EXTI_GetITStatus(EXTI_Line5)!=RESET)|| \
// (EXTI_GetITStatus(EXTI_Line6)!=RESET)|| \
// (EXTI_GetITStatus(EXTI_Line7)!=RESET)|| \
// (EXTI_GetITStatus(EXTI_Line8)!=RESET)|| \
// (EXTI_GetITStatus(EXTI_Line9)!=RESET) )
// {
// HAL_GPIO_EXTI_Callback(GPIO_Pin_5);
// HAL_GPIO_EXTI_Callback(GPIO_Pin_6);
// HAL_GPIO_EXTI_Callback(GPIO_Pin_7);
// HAL_GPIO_EXTI_Callback(GPIO_Pin_8);
// HAL_GPIO_EXTI_Callback(GPIO_Pin_9);
// EXTI_ClearITPendingBit(EXTI_Line5|EXTI_Line6|EXTI_Line7|EXTI_Line8|EXTI_Line9);
// }
if(EXTI_GetITStatus(EXTI_Line5)!=RESET)
{
HAL_GPIO_EXTI_Callback(GPIO_Pin_5);
EXTI_ClearITPendingBit(EXTI_Line5);
}
if(EXTI_GetITStatus(EXTI_Line6)!=RESET)
{
HAL_GPIO_EXTI_Callback(GPIO_Pin_6);
EXTI_ClearITPendingBit(EXTI_Line6);
}
if(EXTI_GetITStatus(EXTI_Line7)!=RESET)
{
HAL_GPIO_EXTI_Callback(GPIO_Pin_7);
EXTI_ClearITPendingBit(EXTI_Line7);
}
if(EXTI_GetITStatus(EXTI_Line8)!=RESET)
{
HAL_GPIO_EXTI_Callback(GPIO_Pin_8);
EXTI_ClearITPendingBit(EXTI_Line8);
}
if(EXTI_GetITStatus(EXTI_Line9)!=RESET)
{
HAL_GPIO_EXTI_Callback(GPIO_Pin_9);
EXTI_ClearITPendingBit(EXTI_Line9);
}
rt_interrupt_leave();
FREE_INT_SP();
}
刚开始,我认为是官方把代码写错了。按照原代码来看,只要5、6、7、8、9线上有一个触发,5、6、7、8、9的中断回调函数就会被依次执行一遍,也就出现了上述问题。
但是我发现了stm32的rtt代码中相同的驱动部分是这样的:
于是我拿stm32做了相同的实验,未发现ch32中出现的问题......
所以这一块儿并不是很明白啥原因,才疏学浅了......
上述三个问题都解决了,希望可以帮大家少踩点坑。
有空会把这些错误提交到RTT仓库中。