千家信息网

SylixOS Zynq平台私有中断绑定

发表于:2024-10-12 作者:千家信息网编辑
千家信息网最后更新 2024年10月12日,1. 概述本篇主要介绍在Zynq平台编写中断相关的驱动程序时,涉及CPU私有中断的相关绑定办法。2. 私有中断简介私有中断是多核CPU上特有的中断,私有中断只能被其所有者核心获取和响应,不会被其他核发
千家信息网最后更新 2024年10月12日SylixOS Zynq平台私有中断绑定

1. 概述

本篇主要介绍在Zynq平台编写中断相关的驱动程序时,涉及CPU私有中断的相关绑定办法。

2. 私有中断简介

私有中断是多核CPU上特有的中断,私有中断只能被其所有者核心获取和响应,不会被其他核发现。常见的私有中断有全局定时器,私有看门狗定时器,私有定时器等,Zynq平台上还有来自PL的FIQ\IRQ。

3. 私有中断的绑定方法

3.1 常规共享中断绑定

Zynq平台使用的是GIC通用中断框架,常规的共享中断绑定和普通的中断绑定没有区别,在SylixOS上直接调用API_InterVectorConnectAPI_InterVectorEnable这两个函数即可绑定,绑定后中断可由任意一个CPU核心响应。

3.2 私有中断绑定

私有中断只能有所有者核心获取和响应,因此对应的中断和中断服务是绑定在相关的CPU核心上。在SylixOS下绑定私有中断需要让常规共享中断的绑定流程在对应CPU核心上完成才能成功绑定。即在驱动绑定私有中断的时候创建一个绑定在对应CPU核心上的绑定线程,然后由这个绑定线程去完成私有中断绑定。绑定流程如图 3.1示。


图 3.1私有中断绑定流程

Zynq平台31号私有定时器中断绑定框架如程序清单 3.1所示。

程序清单 3.1 Zynq平台31号私有定时器中断绑定框架

#define ZYNQ_VECTOR_NIRQ     31         /* 31号私有中断           */static LW_HANDLE  _G_bindthread       = LW_OBJECT_HANDLE_INVALID;static LW_HANDLE  _G_syncSignal       = LW_OBJECT_HANDLE_INVALID; /***************************************************************************** 函数名称: __nIrqIsr** 功能描述: 中断服务程序** 输 入  : pvArg** 输 出  : NONE** 返  回  : LW_NULL***************************************************************************/static irqreturn_t __nIrqIsr (PVOID  pvArg){return  LW_IRQ_HANDLED;}/***************************************************************************** 函数名称: __bindThread** 功能描述: 私有中断绑定线程** 输 入  : pvArg** 输 出  : NONE** 返  回  : LW_NULL***************************************************************************/static PVOID  __bindThread (PVOID  pvArg){API_SemaphoreBPend(_G_syncSignal, LW_OPTION_WAIT_INFINITE);              /* 等待同步信号量      */API_InterVectorConnect(ZYNQ_VECTOR_NIRQ,             /* 连接中断服务程序    */                     (PINT_SVR_ROUTINE)__nIrqIsr,                     (PVOID)NULL,                     "nIrq");API_InterVectorEnable(ZYNQ_VECTOR_NIRQ);             /* 使能中断            */}/***************************************************************************** 函数名称: __nIrqInit** 功能描述: 中断服务初始化** 输 入  : NONE** 输 出  : NONE** 返  回  : 成功返回ERROR_NONE,失败返回PX_ERROR***************************************************************************/INT  __nIrqInit (VOID){LW_CLASS_CPUSET            cpuset; _G_syncSignal = API_SemaphoreBCreate("SYNCSEM",     /* 创建同步等待信号    */                                            0,                                            LW_OPTION_OBJECT_GLOBAL,                                            LW_NULL);if (_G_syncSignal == LW_OBJECT_HANDLE_INVALID) {    /*判断信号量创建是否成功*/     printk ("BIND signal init failed !\r\n");     return PX_ERROR;}/* *  设置线程CPU绑定属性*/LW_CPU_ZERO(&cpuset);LW_CPU_SET(0, &cpuset);_G_bindthread = API_ThreadCreate("bindThread",      /* 创建绑定线程          */                                   __bindThread,                                   LW_NULL,                                      LW_NULL);if (_G_bindthread == LW_OBJECT_HANDLE_INVALID) {  /*判断绑定线程是否创建成功*/     printk ("BIND thread init failed !\r\n");     return PX_ERROR;} API_ThreadSetAffinity(_G_bindthread,               /* 将绑定线程设置到CPU0上*/sizeof(cpuset), &cpuset);    API_SemaphoreBPost(_G_syncSignal);                 /* 发送信号启动绑定线程    */}


0