zhaoxiawanqiu 发表于 2024-7-27 14:06

基于RISCV指令集的中科昊芯DSP(280025C)开发板测试(一)——GPIO中断

本帖最后由 zhaoxiawanqiu 于 2024-7-27 14:08 编辑

<p>昊芯入门学习记录-GPIO中断</p>

<p>任务目标:<br />
使用外中断触发一GPIO控制开发板上两LED状态翻转</p>

<p>&nbsp;</p>

<p>一、如下图所示,知道GPIO31、34经过一缓冲器分别接到LED6、LED7的阴极,故在本实验中IO端口低电平有效。</p>

<p> &nbsp;</p>

<p>&nbsp;</p>

<p>二、根据Haawking IDE的引导创建一个新的工程,选择280025C的型号,程序烧写至Flash中。</p>

<p>略</p>

<p>三、要实现任务目标主函数所使用资源分析</p>

<p>1、时钟和外设配置函数: Device_Init(); &nbsp; &nbsp;创建工程自动生成(160Mhz,本实验不考虑到功耗算力等条件,故不需要调整)<br />
&nbsp;&nbsp; &nbsp;系统默认时钟来自内部OSC1,10MHZ,经PLL模块倍频16倍为160Mhz。默认LSPCLK分频号为2,分频系数为4,为40Mhz。</p>

<p>下面是该函数,在Device.c里面,主函数里面会自己调用,不用管。</p>

<div style="text-align: center;"></div>

<p>2、中断模组初始化和向量表初始化函数; interrupt.h 里面调用,&nbsp; &nbsp;Interrupt_initModule();&nbsp;Interrupt_initVectorTable();上述两个函数在驱动库里面interrupt.c文件里面编写,实现中断的初始化功能,需要在主函数中调用它们。</p>

<div style="text-align: center;"></div>

<p>&nbsp;</p>

<p><br />
3、GPIO初始化,配置GPIO9为输入模式(为外中断触发引脚),GPIO31、34为输出模式,gpio.c里面调用相关配置函数</p>

<p>&nbsp;&nbsp; &nbsp;GPIO_setPinConfig(uint32_t pinConfig);</p>

<p>&nbsp;&nbsp;&nbsp;&nbsp;该函数在配置IO口的时候使用,传入宏定义的IO地址,如GPIO_9_GPIO9为GPIO9的地址的宏,无返回值。<br />
&nbsp;&nbsp; &nbsp;GPIO_setPadConfig(uint32_t pin, uint32_t pinType)</p>

<p>&nbsp; &nbsp; 该函数为配置IO口的类型,参数一为端口号(直接给数字即可),参数二为端口类型,传入宏定义好的类型名即可,如GPIO_PIN_TYPE_PULLUP为推挽模式,无返回值。<br />
&nbsp; &nbsp; GPIO_setQualificationMode(uint32_t pin, GPIO_QualificationMode qualification);</p>

<p>&nbsp;&nbsp;&nbsp;&nbsp;该函数为配置IO口的时钟,参数一为端口号(直接给数字即可),参数二为时钟配置,传入宏定义好的时钟设置即可,如GPIO_QUAL_SYNC为同步SYSCLK时钟,无返回值。<br />
&nbsp;&nbsp; &nbsp;GPIO_setDirectionMode(uint32_t pin, GPIO_Direction pinIO);</p>

<p>&nbsp;&nbsp;&nbsp;&nbsp;该函数为配置IO口的输入输出方向,参数一为端口号(直接给数字即可),参数二为方向配置,传入宏定义好的参数即可,如GPIO_DIR_MODE_IN为输入模式,无返回值。</p>

<div style="text-align: center;"></div>

<p>&nbsp;在main.c里面写一个GPIO初始化函数,调用上述四个配置函数,然后在主函数里面调用该初始化函数,并且给31、34引脚分别写1、0。如下图示:</p>

<p>&nbsp;</p>

<div style="text-align: center;"></div>

<p><br />
4、GPIO9中断配置,调用gpio.h相关函数,在gpio.h里面可以看到相关函数详细信息,这里用图片给出。</p>

<div style="text-align: center;"></div>

<p>&nbsp;在主函数调用这三个函数,并给合适参数即可实现gpio9的中断配置</p>

<p>&nbsp;&nbsp;&nbsp;&nbsp;GPIO_setInterruptType(GPIO_INT_XINT1, GPIO_INT_TYPE_RISING_EDGE);//给中断入口号,配置成上升沿触发<br />
&nbsp; &nbsp; GPIO_setInterruptPin(9, GPIO_INT_XINT1);//设置端口9为中断引脚,给入口号<br />
&nbsp; &nbsp; GPIO_enableInterrupt(GPIO_INT_XINT1);//使能该中断IO入口号</p>

<p><br />
5、中断使能寄存器、使能端口地址、全局使能,调用interrupt.h里面相关函数</p>

<div style="text-align: center;"></div>

<p>再主函数中调用这三个函数,实现中断配置</p>

<p>&nbsp;&nbsp;&nbsp;&nbsp;Interrupt_register(INT_XINT1,&amp;GPIO9_INT_Handler);//给定中断入口号对应地址宏定义参数,给定中断服务函数地址。<br />
&nbsp; &nbsp; Interrupt_enable(INT_XINT1);//使能对应中断入口<br />
&nbsp; &nbsp; Interrupt_enableGlobal();//使能全局中断<br />
5.1、编写中断服务函数如下,在里面翻转两引脚电平,然后清除中断组号即可,该函数在main.c前面需要声明。</p>

<p>__interrupt void GPIO9_INT_Handler(void)<br />
{</p>

<p>&nbsp;&nbsp; &nbsp;GPIO_togglePin(31);<br />
&nbsp;&nbsp; &nbsp;GPIO_togglePin(34);</p>

<p>&nbsp;&nbsp; &nbsp;Interrupt_clearACKGroup(INTERRUPT_ACK_GROUP1);</p>

<p>}</p>

<p>三、整体实现代码,该任务仅在main.c里面编写相关函数,代码如下;</p>

<p>#include &lt;syscalls.h&gt;<br />
#include &quot;IQmathLib.h&quot;<br />
#include &quot;hx_intrinsics.h&quot;<br />
#include &quot;driverlib.h&quot;<br />
#include &quot;device.h&quot;<br />
#include &quot;hx_fintdiv.h&quot;</p>

<p>void User_GPIO_Init(void);<br />
__interrupt void GPIO9_INT_Handler(void);</p>

<p>int main(void)<br />
{<br />
&nbsp;&nbsp; &nbsp;//<br />
&nbsp;&nbsp; &nbsp;// Intialize device clock and peripherals<br />
&nbsp;&nbsp; &nbsp;//<br />
&nbsp; &nbsp; Device_init();<br />
&nbsp; &nbsp; //init gpio pin<br />
&nbsp; &nbsp; User_GPIO_Init();</p>

<p>&nbsp; &nbsp; GPIO_writePin(31, 1);<br />
&nbsp; &nbsp; GPIO_writePin(34, 0);</p>

<p>&nbsp; &nbsp; Interrupt_initModule();<br />
&nbsp; &nbsp; Interrupt_initVectorTable();</p>

<p>&nbsp; &nbsp; GPIO_setInterruptType(GPIO_INT_XINT1, GPIO_INT_TYPE_RISING_EDGE);<br />
&nbsp; &nbsp; GPIO_setInterruptPin(9, GPIO_INT_XINT1);<br />
&nbsp; &nbsp; GPIO_enableInterrupt(GPIO_INT_XINT1);</p>

<p><br />
&nbsp; &nbsp; Interrupt_register(INT_XINT1,&amp;GPIO9_INT_Handler);<br />
&nbsp; &nbsp; Interrupt_enable(INT_XINT1);<br />
&nbsp; &nbsp; Interrupt_enableGlobal();</p>

<p>&nbsp; &nbsp; while(1);<br />
&nbsp; &nbsp; return 0;<br />
}</p>

<p>__interrupt void GPIO9_INT_Handler(void)<br />
{</p>

<p>&nbsp;&nbsp; &nbsp;GPIO_togglePin(31);<br />
&nbsp;&nbsp; &nbsp;GPIO_togglePin(34);</p>

<p>&nbsp;&nbsp; &nbsp;Interrupt_clearACKGroup(INTERRUPT_ACK_GROUP1);</p>

<p>}</p>

<p>&nbsp;void User_GPIO_Init(void)<br />
{<br />
&nbsp;&nbsp; &nbsp;//设置GPIO9为输入模式,为中断做准备<br />
&nbsp;&nbsp; &nbsp;GPIO_setPinConfig(GPIO_9_GPIO9);<br />
&nbsp;&nbsp; &nbsp;GPIO_setPadConfig(9, GPIO_PIN_TYPE_INVERT);<br />
&nbsp;&nbsp; &nbsp;GPIO_setQualificationMode(9, GPIO_QUAL_SYNC);<br />
&nbsp;&nbsp; &nbsp;GPIO_setDirectionMode(9, GPIO_DIR_MODE_IN);</p>

<p>&nbsp;&nbsp; &nbsp;//设置GPIO34,GPIO31为输出模式,控制LED<br />
&nbsp;&nbsp; &nbsp;GPIO_setPinConfig(GPIO_31_GPIO31);<br />
&nbsp;&nbsp; &nbsp;GPIO_setPadConfig(31, GPIO_PIN_TYPE_PULLUP);<br />
&nbsp;&nbsp; &nbsp;GPIO_setQualificationMode(31, GPIO_QUAL_SYNC);<br />
&nbsp;&nbsp; &nbsp;GPIO_setDirectionMode(31, GPIO_DIR_MODE_OUT);</p>

<p>&nbsp;&nbsp; &nbsp;GPIO_setPinConfig(GPIO_34_GPIO34);<br />
&nbsp;&nbsp; &nbsp;GPIO_setPadConfig(34, GPIO_PIN_TYPE_PULLUP);<br />
&nbsp;&nbsp; &nbsp;GPIO_setQualificationMode(34, GPIO_QUAL_SYNC);<br />
&nbsp;&nbsp; &nbsp;GPIO_setDirectionMode(34, GPIO_DIR_MODE_OUT);<br />
}<br />
//<br />
// End of File<br />
&nbsp;</p>

<p>四、实验结果与分析</p>

<p>上电下载程序,按下复位按键后LED6、LED7分别为灭、亮状态如下图:</p>

<div style="text-align: center;"></div>

<p>然后间断不停GPIO9高电平,切换两灯状态6ae6fc273cab17038830353f3824b4ab</p>

<p>&nbsp;</p>

<p>五、实验总结</p>

<p>本次实验测试了GPIO中断的功能,使用到了GPIO、中断相关的配置函数,了解了系统时钟配置,通过翻转LED状态完成功能验证。中间也遇到了一个测试问题,就是IO9接插上一杜邦线后就不停的触发中断,此时杜邦线另一端处于悬空的状态,大概是噪声或是我使用的杜邦线材质等原因干扰造成中断一直被触发,我后面测试的时候就用了一个万用表表笔不停触碰GPIO9也起到了相同效果。正常的解决思路:加电容、加上下拉电阻在外中断触发引脚,只要不让该引脚处于浮空状态即可。</p>

通途科技 发表于 2024-7-30 11:44

页: [1]
查看完整版本: 基于RISCV指令集的中科昊芯DSP(280025C)开发板测试(一)——GPIO中断