OpenEdv-开源电子网

 找回密码
 立即注册
正点原子全套STM32/Linux/FPGA开发资料,上千讲STM32视频教程免费下载...
查看: 807|回复: 5

[XILINX] 求助:zynq-7000中运行FreeRTOS该如何设置串口中断?

[复制链接]

3

主题

10

帖子

0

精华

新手上路

积分
31
金钱
31
注册时间
2026-3-17
在线时间
7 小时
发表于 2026-5-6 15:19:48 | 显示全部楼层 |阅读模式
1金钱
我按照网上找到的方法设置串口中断,FreeRTOS任务可以执行,但中断不能执行,请高手指点......

extern XScuGic xInterruptController;              //中断控制器驱动程序实例
XUartPs Uart_Ps1;           //串口驱动程序实例


int main()
{
...
}

static void prvUartIntTestTask( void *pvParameters )
{
        const TickType_t x1second = pdMS_TO_TICKS(DELAY_1_SECOND);
        uart_int_init(&Uart_Ps1,&xInterruptController);                //串口及中断初始化

        for(;;)
        {
                vTaskDelay( x1second );
        }
}



//UART及中断初始化函数
int uart_int_init(XUartPs* uart_ps,XScuGic *intc)
{
    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);

    //为中断设置中断处理函数
    XScuGic_Connect(intc, UART_INT_IRQ_ID,
            (Xil_ExceptionHandler) uart_intr_handler,(void *) uart_ps);
    //设置UART的中断触发方式
    XUartPs_SetInterruptMask(uart_ps, XUARTPS_IXR_RXOVR);
    //设置中断优先级:0x00代表最高优先级;0x1代表电平触发;0x3代表上升沿触发
    XScuGic_SetPriorityTriggerType(intc,UART_INT_IRQ_ID,8,0x1);
    //使能GIC中的串口中断
    XScuGic_Enable(intc, UART_INT_IRQ_ID);
    XUartPs_EnableUart(uart_ps);

    return XST_SUCCESS;
}


回复

使用道具 举报

2

主题

14

帖子

0

精华

初级会员

Rank: 2

积分
89
金钱
89
注册时间
2015-9-28
在线时间
19 小时
发表于 2026-5-7 08:28:15 | 显示全部楼层
自己定义的中断,只能在vTaskStartScheduler(); 以后执行中断初始化,因为xInterruptController 中断控制器实例在vTaskStartScheduler();中初始化,只有在中断控制器初始化之后才能连接其他中断;
回复

使用道具 举报

3

主题

10

帖子

0

精华

新手上路

积分
31
金钱
31
注册时间
2026-3-17
在线时间
7 小时
 楼主| 发表于 2026-5-7 13:39:43 | 显示全部楼层
zh9454 发表于 2026-5-7 08:28
自己定义的中断,只能在vTaskStartScheduler(); 以后执行中断初始化,因为xInterruptController 中断控制器 ...

我是在任务中进行串口中断初始化的。
static void prvUartIntTestTask( void *pvParameters )
{
        const TickType_t x1second = pdMS_TO_TICKS(DELAY_1_SECOND);
        uart_int_init(&Uart_Ps1,&xInterruptController);                //串口及中断初始化

        for(;;)
        {
                vTaskDelay( x1second );
        }
}
回复

使用道具 举报

3

主题

10

帖子

0

精华

新手上路

积分
31
金钱
31
注册时间
2026-3-17
在线时间
7 小时
 楼主| 发表于 2026-5-7 15:18:06 | 显示全部楼层
我现在调试程序时执行到下面这一行就退不出来
//为中断设置中断处理函数
    XScuGic_Connect(intc, UART_INT_IRQ_ID,
            (Xil_ExceptionHandler) uart_intr_handler,(void *) uart_ps);
回复

使用道具 举报

2

主题

14

帖子

0

精华

初级会员

Rank: 2

积分
89
金钱
89
注册时间
2015-9-28
在线时间
19 小时
发表于 2026-5-7 16:51:51 | 显示全部楼层
可以试着把默认的最小任务栈空间调大一些试试
回复

使用道具 举报

3

主题

10

帖子

0

精华

新手上路

积分
31
金钱
31
注册时间
2026-3-17
在线时间
7 小时
 楼主| 发表于 2026-5-9 11:23:43 | 显示全部楼层
portZynq7000.c 中的中断控制器xInterruptController似乎没有初始化,初始化函数void FreeRTOS_SetupTickInterrupt( void )都是灰色的,前面有一个伪判断语句#ifndef XPAR_XILTIMER_ENABLED;这个应该在哪里定义啊?应该放在FreeRTOSConfig.h中定义吗?

XScuGic xInterruptController;         /* Interrupt controller instance */

/*-----------------------------------------------------------*/

#ifndef XPAR_XILTIMER_ENABLED
void FreeRTOS_SetupTickInterrupt( void )
{
BaseType_t xStatus;
extern void FreeRTOS_Tick_Handler( void );
XScuTimer_Config *pxTimerConfig;
XScuGic_Config *pxGICConfig;
const uint8_t ucRisingEdge = 3;

        /* This function is called with the IRQ interrupt disabled, and the IRQ
        interrupt should be left disabled.  It is enabled automatically when the
        scheduler is started. */

        /* Ensure XScuGic_CfgInitialize() has been called.  In this demo it has
        already been called from prvSetupHardware() in main(). */
        pxGICConfig = XScuGic_LookupConfig( XPAR_SCUGIC_SINGLE_DEVICE_ID );
        xStatus = XScuGic_CfgInitialize( &xInterruptController, pxGICConfig, pxGICConfig->CpuBaseAddress );
        configASSERT( xStatus == XST_SUCCESS );
        ( void ) xStatus; /* Remove compiler warning if configASSERT() is not defined. */

        /* The priority must be the lowest possible. */
        XScuGic_SetPriorityTriggerType( &xInterruptController, XPAR_SCUTIMER_INTR, portLOWEST_USABLE_INTERRUPT_PRIORITY << portPRIORITY_SHIFT, ucRisingEdge );

        /* Install the FreeRTOS tick handler. */
        xStatus = XScuGic_Connect( &xInterruptController, XPAR_SCUTIMER_INTR, (Xil_ExceptionHandler) FreeRTOS_Tick_Handler, ( void * ) &xTimer );
        configASSERT( xStatus == XST_SUCCESS );
        ( void ) xStatus; /* Remove compiler warning if configASSERT() is not defined. */

        /* Initialise the timer. */
        pxTimerConfig = XScuTimer_LookupConfig( XPAR_SCUTIMER_DEVICE_ID );
        xStatus = XScuTimer_CfgInitialize( &xTimer, pxTimerConfig, pxTimerConfig->BaseAddr );
        configASSERT( xStatus == XST_SUCCESS );
        ( void ) xStatus; /* Remove compiler warning if configASSERT() is not defined. */

        /* Enable Auto reload mode. */
        XScuTimer_EnableAutoReload( &xTimer );

        /* Ensure there is no prescale. */
        XScuTimer_SetPrescaler( &xTimer, 0 );

        /* Load the timer counter register.
         * The Xilinx implementation of generating run time task stats uses the same timer used for generating
         * FreeRTOS ticks. In case user decides to generate run time stats the timer time out interval is changed
         * as "configured tick rate * 10". The multiplying factor of 10 is hard coded for Xilinx FreeRTOS ports.
         */
#if (configGENERATE_RUN_TIME_STATS == 1)
        XScuTimer_LoadTimer( &xTimer, XSCUTIMER_CLOCK_HZ / (configTICK_RATE_HZ * 10) );
#else
        XScuTimer_LoadTimer( &xTimer, XSCUTIMER_CLOCK_HZ / configTICK_RATE_HZ );
#endif

        /* Start the timer counter and then wait for it to timeout a number of
        times. */
        XScuTimer_Start( &xTimer );

        /* Enable the interrupt for the xTimer in the interrupt controller. */
        XScuGic_Enable( &xInterruptController, XPAR_SCUTIMER_INTR );

        /* Enable the interrupt in the xTimer itself. */
        FreeRTOS_ClearTickInterrupt();
        XScuTimer_EnableInterrupt( &xTimer );
}
/*-----------------------------------------------------------*/

void FreeRTOS_ClearTickInterrupt( void )
{
        XScuTimer_ClearInterruptStatus( &xTimer );
}
#else
void TimerCounterHandler(void *CallBackRef, u32 TmrCtrNumber)
{
        (void) CallBackRef;
        (void) TmrCtrNumber;
        FreeRTOS_Tick_Handler();
}
回复

使用道具 举报

您需要登录后才可以回帖 登录 | 立即注册

本版积分规则



关闭

原子哥极力推荐上一条 /1 下一条

正点原子公众号

如发现本坛存在违规或侵权内容, 请点击这里发送邮件举报 (或致电020-38271790)。请提供侵权说明和联系方式。我们将及时审核依法处理,感谢配合。

QQ|手机版|OpenEdv-开源电子网 ( 粤ICP备12000418号-1 )

GMT+8, 2026-5-27 22:18

Powered by OpenEdv-开源电子网

© 2001-2030 OpenEdv-开源电子网

快速回复 返回顶部 返回列表