4796|8

76

帖子

0

TA的资源

一粒金砂(初级)

楼主
 

关于CE5.0静态中断处理方式过程的一个疑惑 [复制链接]

   最近在折腾DM9000移植上CE5.0上,使用的是S3C2440的CE5.0官方BSP。打算使用静态中断处理的方法:
系统启动:ARMInit->OEMInit->OALIntrInit->OALIntrMapInit->(#ifdef OAL_BSP_CALLBACKS--BSPIntrInit->OALIntrStaticTranslate) ;
中断初始化:InterruptInitialize(驱动程序)->OEMInterruptEnable(微软实现)->OALIntrTranslateSysIntr(数据校验,把逻辑中断号变成IRQ号)->OALIntrEnableIrqs(OEM实现,通过IRQ号使能自定义的中断)->BSPIntrRequestIrqs->BSPIntrEnableIrq;
ISR实现:OEMInterruptHandler->(NKCallIntrChain)/OALIntrTranslateIrq  返回发生中断的IRQ对应的逻辑中断;
中断结束:InterruptDone->OEMInterruptDone->OALIntrDoneIrqs(BSPIntrDoneIrq);
------------------------------------------------
1.在具体中断初始化过程中,IST线程中调用InterruptInitialize(DWORD idInt,,,),进而调用OEMInterruptEnable(DWORD idInt,,):

  1. BOOL OEMInterruptEnable(DWORD sysIntr, LPVOID pvData, DWORD cbData)
  2. {
  3.     BOOL rc = FALSE;
  4.     const UINT32 *pIrqs;
  5.     UINT32 count;

  6.     OALMSG(OAL_INTR&&OAL_VERBOSE,
  7.         (L"+OEMInterruptEnable(%d, 0x%x, %d)\r\n", sysIntr, pvData, cbData
  8.     ));

  9.     // SYSINTR_VMINI & SYSINTR_TIMING are special cases
  10.     if (sysIntr == SYSINTR_VMINI || sysIntr == SYSINTR_TIMING) {
  11.         rc = TRUE;
  12.         goto cleanUp;
  13.     }

  14.     // Obtain the SYSINTR's underlying IRQ number
  15.    [color=#FF0000] if (!OALIntrTranslateSysIntr(sysIntr, &count, &pIrqs)) {[/color]        // Indicate invalid SysIntr
  16.         OALMSG(OAL_ERROR, (
  17.             L"ERROR: OEMInterruptEnable: IRQs are undefined for SysIntr %d\r\n",
  18.             sysIntr
  19.         ));
  20.         goto cleanUp;
  21.     }

  22.     // Enable the interrupt
  23.     rc = [color=#FF0000]OALIntrEnableIrqs(count, pIrqs);[/color]

  24. cleanUp:   
  25.     OALMSG(OAL_INTR&&OAL_VERBOSE, (L"-OEMInterruptEnable(rc = 1)\r\n"));
  26.     return rc;
  27. }
复制代码


再调用OALIntrTranslateSysIntr(DWORD idInt,,)函数:

  1. BOOL OALIntrTranslateSysIntr(UINT32 [color=#FF0000]sysIntr[/color], UINT32 *pCount, const UINT32 **ppIrqs) //第一个参数是输入,后两个是输出参数
  2. {
  3.     BOOL rc;

  4.     OALMSG(OAL_INTR&&OAL_VERBOSE, (L"+OALTranslateSysIntr(%d)\r\n", sysIntr));
  5.    
  6.     // Valid SYSINTR?
  7.     if (sysIntr >= SYSINTR_MAXIMUM) {
  8.         rc = FALSE;
  9.         goto cleanUp;
  10.     }
  11.     *pCount = 1;
  12.     *ppIrqs = &g_oalSysIntr2Irq[[color=#FF0000]sysIntr[/color]];//通过g_oalSysIntr2Irq数组转换得到IRQ号
  13.     rc = TRUE;

  14. cleanUp:
  15.     OALMSG(OAL_INTR&&OAL_VERBOSE, (L"-OALTranslateSysIntr(rc = %d)\r\n", rc));
  16.     return rc;
  17. }
复制代码


2.OALIntrTranslateSysIntr()函数又调用OALIntrEnableIrqs()函数:

  1. BOOL OALIntrEnableIrqs(UINT32 count, const UINT32 *[color=#FF0000]pIrqs[/color])
  2. {
  3.     BOOL rc = TRUE;
  4.     UINT32 i, mask, irq;

  5.     OALMSG(OAL_INTR&&OAL_FUNC, (
  6.         L"+OALIntrEnableIrqs(%d, 0x%08x)\r\n", count, [color=#FF0000]pIrqs[/color]
  7.     ));

  8.     for (i = 0; i < count; i++) {
  9. #ifndef OAL_BSP_CALLBACKS
  10.         [color=#FF0000]irq = pIrqs[i];[/color]
  11. #else
  12.         // Give BSP chance to enable irq on subordinate interrupt controller
  13.         [color=#FF0000]irq = BSPIntrEnableIrq(pIrqs[i]);//在未使用到多级中断控制器下,未作实际操作,直接返回pIrqs[i][/color]
  14. #endif
  15.         if (irq == OAL_INTR_IRQ_UNDEFINED) continue;
  16.         // Depending on IRQ number use internal or external mask register
  17.         if (irq <= IRQ_ADC) {
  18.             // Use interrupt mask register
  19.             CLRREG32(&g_pIntrRegs->INTMSK, 1 << irq);
  20.         } else if (irq <= IRQ_EINT7) {
  21.             // Use external mask register
  22.             CLRREG32(&g_pIntrRegs->INTMSK, 1 << IRQ_EINT4_7);        //IRQ_EINT4_7~4
  23.             CLRREG32(&g_pPortRegs->EINTMASK, 1 << (irq - IRQ_EINT4 + 4));        //IRQ_EINT4~32
  24.         } else if (irq <= IRQ_EINT23) {
  25.             // Use external mask register
  26.             mask = 1 << (irq - IRQ_EINT4 + 4);
  27.             OUTREG32(&g_pPortRegs->EINTPEND, mask);
  28.             CLRREG32(&g_pPortRegs->EINTMASK, mask);
  29.             mask = 1 << IRQ_EINT8_23;
  30.             if ((INREG32(&g_pIntrRegs->INTPND) & mask) != 0) {
  31.                 OUTREG32(&g_pIntrRegs->INTPND, mask);
  32.             }
  33.             CLRREG32( &g_pIntrRegs->INTMSK, 1 << IRQ_EINT8_23);
  34.         } else {
  35.             rc = FALSE;
  36.         }
  37.     }        

  38.     OALMSG(OAL_INTR&&OAL_FUNC, (L"-OALIntrEnableIrqs(rc = %d)\r\n", rc));
  39.     return rc;   
  40. }
复制代码

这里就有疑问了,通过OALIntrTranslateSysIntr函数转换sysIntr成为IRQ号,但是这个IRQ号只拿来做了OAL调试输出信息的参数,后面的使能中断部分并没有使用到这个IRQ号啊?
   而是使用了pIrqs这个数组,OALIntrRequestIrqs()和BSPIntrRequestIrqs()【功能是:获取设备的IRQ号(如通过IO Address获取该设备对应的IRQ)】,但是在中断流程中没有发现对这两个函数的调用啊?
   何解啊?
   我该怎么办?
   请各位高手相助!

最新回复

对三星的片子,CLRREG32(&g_pIntrRegs->INTMSK, 1 < < irq);这个就是打开中断。XScale的正好相反,具体要看芯片手册。中断号动态还是静态映射只是处理上的不同,对性能什么的没什么区别。  详情 回复 发表于 2008-12-29 13:38
点赞 关注

回复
举报

72

帖子

0

TA的资源

一粒金砂(初级)

沙发
 
你在我的博客留言我看了,我已经回复了
——刚开始我也陷入了圈套。这个静态中断只初始化了网卡的一个中断而已。5.0下其他中断全部用kernelIoControl来动态申请。这样做比较好。你可以随便找个5.0 2440BSP的驱动看看。就一切OK了。睡觉!了
 
 

回复

72

帖子

0

TA的资源

一粒金砂(初级)

板凳
 
5.0的中断是动态申请的,和4.2的不一样,楼主估计被这个弄晕了
 
 
 

回复

67

帖子

0

TA的资源

一粒金砂(初级)

4
 
引用 2 楼 xyj0663 的回复:
5.0的中断是动态申请的,和4.2的不一样,楼主估计被这个弄晕了


对了,估计我的老博客没有更正过来,楼主也跟着跳进来了,哈哈,其实我后面我重新写了一篇博客更正的,楼主不妨看看。
 
 
 

回复

67

帖子

0

TA的资源

一粒金砂(初级)

5
 
大概看过gooogleman的《KernelIoControl和OEMIoControl的分析和使用》
我有疑问
1,KernelIoControl在IOCTL_HAL_REQUEST_SYSINTR下,除了“动态”得到irq对应的SYSINTR,还有别的吗?有允许irq对应的中断吗?
2,InterruptInitialize的作用可以理解为打开SYSINTR对应的中断吗?如果可以,OALIntrEnableIrqs这个函数就是打开中断的函数吧?(OALIntrEnableIrqs这个函数是bsp里的,即oem实现。)那么我怎么看不懂,CLRREG32(&g_pIntrRegs->INTMSK, 1 << irq);这个清除中断掩码,是打开中断吗?对2440不熟悉。
3,如果新加的驱动,在OALIntrEnableIrqs里没有打开对应中断的代码,是否自己要添加这些代码呢?

我想楼主想问的应该是这些吧。
 
 
 

回复

84

帖子

0

TA的资源

一粒金砂(初级)

6
 
在这里不多说。这阵子正忙着善后,
找个2440 下的PowerBUTTON 驱动一看就知道了。一路跟上去,就知道了
有什么新发现,记得在我博客后留言哦。
 
 
 

回复

78

帖子

0

TA的资源

一粒金砂(初级)

7
 
引用 2 楼 xyj0663 的回复:
5.0的中断是动态申请的,和4.2的不一样,楼主估计被这个弄晕了

应该5.0中有两种中断方式吧?动态和静态。
我记得在网上很多人都这样说啊
 
 
 

回复

81

帖子

0

TA的资源

一粒金砂(初级)

8
 
引用 6 楼 iwillbeback008 的回复:
引用 2 楼 xyj0663 的回复:
5.0的中断是动态申请的,和4.2的不一样,楼主估计被这个弄晕了

应该5.0中有两种中断方式吧?动态和静态。
我记得在网上很多人都这样说啊


是有,但是有未必用了
看看代码就知道。我觉得除非在OAL时候使用的中断,最好不要使用静态中断,因为静态放在OAL初始化,这样不利于管理。并且会导致OAL代码庞大。
放在驱动中比较合理,但是实时性估计会受影响,仅仅是个人看法。
 
 
 

回复

75

帖子

0

TA的资源

一粒金砂(初级)

9
 
对三星的片子,CLRREG32(&g_pIntrRegs->INTMSK, 1 < < irq);这个就是打开中断。XScale的正好相反,具体要看芯片手册。中断号动态还是静态映射只是处理上的不同,对性能什么的没什么区别。
 
 
 

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

随便看看
查找数据手册?

EEWorld Datasheet 技术支持

相关文章 更多>>
关闭
站长推荐上一条 1/6 下一条

 
EEWorld订阅号

 
EEWorld服务号

 
汽车开发圈

About Us 关于我们 客户服务 联系方式 器件索引 网站地图 最新更新 手机版

站点相关: 国产芯 安防电子 汽车电子 手机便携 工业控制 家用电子 医疗电子 测试测量 网络通信 物联网

北京市海淀区中关村大街18号B座15层1530室 电话:(010)82350740 邮编:100190

电子工程世界版权所有 京B2-20211791 京ICP备10001474号-1 电信业务审批[2006]字第258号函 京公网安备 11010802033920号 Copyright © 2005-2025 EEWORLD.com.cn, Inc. All rights reserved
快速回复 返回顶部 返回列表