首先在 vivado 中创建工程,由于本次使用的是 GPIO 中的 MIO 进行中断,所以在 vivado 中只需要添加一个 ZYNQ 的内核即可。然后在 SDK 中编写代码,代码如下
#include <stdio.h>
#include "platform.h"
#include "xgpiops.h"
#include "xgpiops_hw.h"
#include "XSCUGIC.H"
#include "XSCUGIC_HW.H"
#define key 50 //MIO引脚,是一个按键
//触发中断时会给3个信息,触发中断引脚信息,Bank信息,Status为GPIO bank的中断状态
static void GpioHandler(void *CallBackRef, int Bank, u32 Status)
{
if (Status ==0 ) return ; //没有中断信息直接返回
XGpioPs* pGpioPs=(XGpioPs*)CallBackRef; //定义一个GPIO指针方便调用GPIO中断恢复函数
XGpioPs_IntrDisablePin(pGpioPs,key); //禁用指定中断
printf("Gpio Handler ...\n\r"); //中断内容
// while (1 == XGpioPs_ReadPin( pGpioPs , key )); //确认按键按下
// usleep(100*1000); //按键触发,清除按键抖动程序
XGpioPs_IntrEnablePin(pGpioPs,key); //启用指定引脚中断
XGpioPs_IntrClearPin(pGpioPs,key); //清除中断有效位
}
int main()
{
//初始化Dcha和Icha,用于CPU与ARM之间的通讯。提前缓存数据,加快CPU数据读取速度,与ARM和
硬盘之间的的DDR类似
init_platform();
//-------------------------------引脚相关定义------------------------------//
XGpioPs gpio;
XGpioPs_Config *configptr;
//获取基地址每个同样设备的ID都是同样的,所有GPIO系统都是用0作为输入参数
configptr = XGpioPs_LookupConfig(0);
XGpioPs_CfgInitialize(&gpio,configptr,configptr->BaseAddr); //初始化GPIO
//设置GPIO为输入
XGpioPs_SetDirectionPin(&gpio,key,0x0);
//设置GPIO中断模式为上升沿
XGpioPs_SetIntrTypePin(&gpio,key,XGPIOPS_IRQ_TYPE_EDGE_RISING);
//注册GPIO中断函数,发生中断后会调用 GpioHandler 函数,这个函数的第二个参数会传给中断函
数的第一个参数,为了方便在中断函数中处理
XGpioPs_SetCallbackHandler(&gpio,(void *)&gpio,GpioHandler);
//启用引脚中断
XGpioPs_IntrEnablePin(&gpio,key);
//-------------------------------中断相关定义------------------------------//
XScuGic ScuGic;
XScuGic_Config* pScuGicCfg;
//所有中断都是用 XPAR_SCUGIC_SINGLE_DEVICE_ID 获取基地址
pScuGicCfg=XScuGic_LookupConfig(XPAR_SCUGIC_SINGLE_DEVICE_ID);
XScuGic_CfgInitialize(&ScuGic,pScuGicCfg,pScuGicCfg->CpuBaseAddress);
//中断连接,中断数据,中断号,中断函数,回调指针
XScuGic_Connect(&ScuGic,52,(Xil_ExceptionHandler)XGpioPs_IntrHandler,(void *)&gpio);
//中断设设置,中断信息,中断号。中断优先级,高电平触发中断
XScuGic_SetPriorityTriggerType(&ScuGic,52,0xf1,0x01);
//中断使能,使能后就可以使用中断了
XScuGic_Enable(&ScuGic,52);
//初始化异常处理,下面都是异常处理函数
Xil_ExceptionInit();
//设置并打开中断异常处理功能
Xil_ExceptionRegisterHandler(XIL_EXCEPTION_ID_INT,
(Xil_ExceptionHandler)XScuGic_InterruptHandler,&ScuGic);
//启用中断异常
Xil_ExceptionEnable();
//--------------------------------------------------------------------//
cleanup_platform(); //关闭Dcha和Icha节约资源
return 0;
}