zynq 同时使用ps端uart和定时器,定时器不能使用

贴出部分代码,想知道同时配置2个中断,需要怎么配置,现在的程序中断可用。定时器中断程序就是1ms进入一次,变量++(定时器中断单独使用可以计时)

#include "xscugic.h"
#include "xuartps.h"
#include "xscutimer.h"

#define UART_DEVICE_ID     XPAR_PS7_UART_0_DEVICE_ID    //PS端  串口设备ID
#define INTC_DEVICE_ID     XPAR_SCUGIC_SINGLE_DEVICE_ID //中断ID
#define UART_INT_IRQ_ID    XPAR_XUARTPS_0_INTR          //PS端  串口中断ID
#define TIMER_DEVICE_ID     XPAR_XSCUTIMER_0_DEVICE_ID   //定时器ID
#define TIMER_IRPT_INTR     XPAR_SCUTIMER_INTR           //定时器中断ID  //29U

#define TIMER_LOAD_VALUE    0x51614                   //定时器装载值

XScuGic Intc;
XUartPs Uart_Ps;           //串口驱动程序实例
XScuTimer Timer;            //定时器驱动程序实例

int uart_init(XUartPs* uart_ps)
{
    int status;
    XUartPs_Config *uart_cfg;

    uart_cfg = XUartPs_LookupConfig(UART_DEVICE_ID);
    if (NULL == uart_cfg)
        return XST_FAILURE;
    status = XUartPs_CfgInitialize(uart_ps, uart_cfg, uart_cfg->BaseAddress);
    if (status != XST_SUCCESS)
        return XST_FAILURE;

    //UART设备自检
    status = XUartPs_SelfTest(uart_ps);
    if (status != XST_SUCCESS)
        return XST_FAILURE;

    //设置工作模式:正常模式
    XUartPs_SetOperMode(uart_ps, XUARTPS_OPER_MODE_NORMAL);
    //设置波特率:115200
    XUartPs_SetBaudRate(uart_ps,115200);
    //设置RxFIFO的中断触发等级
    XUartPs_SetFifoThreshold(uart_ps, 1);

    return XST_SUCCESS;
}

//定时器初始化程序
int timer_init(XScuTimer *timer_ptr)
{
    int status;
    //私有定时器初始化
    XScuTimer_Config *timer_cfg_ptr;
    timer_cfg_ptr = XScuTimer_LookupConfig(TIMER_DEVICE_ID);
    if (NULL == timer_cfg_ptr)
        return XST_FAILURE;
    status = XScuTimer_CfgInitialize(timer_ptr, timer_cfg_ptr,
            timer_cfg_ptr->BaseAddr);
    if (status != XST_SUCCESS)
        return XST_FAILURE;

    XScuTimer_LoadTimer(timer_ptr, TIMER_LOAD_VALUE); // 加载计数周期
    XScuTimer_EnableAutoReload(timer_ptr);            // 设置自动装载模式

    return XST_SUCCESS;
}

//UART中断处理函数
void uart_intr_handler(void *call_back_ref)
{
    XUartPs *uart_instance_ptr = (XUartPs *) call_back_ref;
    u32 rec_data = 0 ;
    u32 isr_status ;                           //中断状态标志

    //读取中断ID寄存器,判断触发的是哪种中断
    isr_status = XUartPs_ReadReg(uart_instance_ptr->Config.BaseAddress,
                   XUARTPS_IMR_OFFSET);
    isr_status &= XUartPs_ReadReg(uart_instance_ptr->Config.BaseAddress,
                   XUARTPS_ISR_OFFSET);

    //判断中断标志位RxFIFO是否触发
    if (isr_status & (u32)XUARTPS_IXR_RXOVR){
        rec_data = XUartPs_RecvByte(XPAR_PS7_UART_0_BASEADDR);
        //清除中断标志
        XUartPs_WriteReg(uart_instance_ptr->Config.BaseAddress,
                XUARTPS_ISR_OFFSET, XUARTPS_IXR_RXOVR) ;
    }
    XUartPs_SendByte(XPAR_PS7_UART_0_BASEADDR,rec_data);
}

//定时器中断处理程序
void timer_intr_handler(void *CallBackRef)
{
    XScuTimer *timer_ptr = (XScuTimer *) CallBackRef;
    //定时器中断用户程序
    time_count++;
    //清除定时器中断标志
    XScuTimer_ClearInterruptStatus(timer_ptr);
}

//串口中断初始化
int uart_intr_init(XScuGic *intc, XUartPs *uart_ps,XScuTimer *timer_ptr)
{
    int status;
    //初始化中断控制器
    XScuGic_Config *intc_cfg;
    intc_cfg = XScuGic_LookupConfig(INTC_DEVICE_ID);
    if (NULL == intc_cfg)
        return XST_FAILURE;
    status = XScuGic_CfgInitialize(intc, intc_cfg,intc_cfg->CpuBaseAddress);
    if (status != XST_SUCCESS)
        return XST_FAILURE;

    //设置并打开中断异常处理功能
    Xil_ExceptionInit();
    Xil_ExceptionRegisterHandler(XIL_EXCEPTION_ID_INT,(Xil_ExceptionHandler)XScuGic_InterruptHandler,(void *)intc);
    Xil_ExceptionEnable();

    //为中断设置中断处理函数
    XScuGic_Connect(intc, UART_INT_IRQ_ID,(Xil_ExceptionHandler) uart_intr_handler,(void *) uart_ps);

    //设置UART的中断触发方式
    XUartPs_SetInterruptMask(uart_ps, XUARTPS_IXR_RXOVR);
    //使能GIC中的串口中断
    XScuGic_Enable(intc, UART_INT_IRQ_ID);

    //设置定时器中断
    XScuGic_Connect(intc, TIMER_IRPT_INTR,(Xil_ExceptionHandler)timer_intr_handler, (void *)timer_ptr);

    XScuGic_Enable(intc, TIMER_IRPT_INTR); //使能GIC中的定时器中断
    XScuTimer_EnableInterrupt(timer_ptr);      //使能定时器中断

    return XST_SUCCESS;
}

int main()
{
    //ps uart_intr
    int status;
    //串口初始化
    status = uart_init(&Uart_Ps);
    if (status == XST_FAILURE) {
        xil_printf("Uart Initial Failed\r\n");
        return XST_FAILURE;
    }

    //ps  time_intr
    int status_time;
    status_time = timer_init(&Timer);     //定时器初始化
    if (status_time != XST_SUCCESS) {
        xil_printf("Timer Initial Failed\r\n");
        return XST_FAILURE;
    }

    //串口中断初始化
     uart_intr_init(&Intc, &Uart_Ps,&Timer);

     while(1);
}
编辑 重设标签(回车键确认) 标为违禁 关闭 合并 删除
压着我头发啦 头像

评论

一开始串口中断初始化和定时器中断初始化分开的,都包含XScuGic_LookupConfig XScuGic_CfgInitialize xil(3个) 。。。主函数两个中断初始化共用输入参数XScuGic Intc;,,,,,也是一样的状态(定时器不可用)

压着我头发啦 头像压着我头发啦 ( 2021-12-31 16:26:20 +0800 )编辑