Arm 手臂饥饿

Arm 手臂饥饿,arm,interrupt,interrupt-handling,Arm,Interrupt,Interrupt Handling,不确定是否有类似的问题。我试图回溯,但找不到,所以它在这里 在我使用ARM Cortex-A9(带GIC的双核)的裸机应用程序中,一些中断源是具有相同优先级的4个FPGA中断(比如IRQ ID 58、59、60、61),其思想是所有中断都在运行时连续触发。我可以说,中断处理程序可以限定为长,但不是很长 GIC检测到所有中断都会触发,并且所有中断都被标记为挂起。问题是,只有两个ID较高的中断(58,59)由CPU处理,使其他两个中断处于饥饿状态。一旦58或59完成,它们的源代码将再次触发,并一次又

不确定是否有类似的问题。我试图回溯,但找不到,所以它在这里

在我使用ARM Cortex-A9(带GIC的双核)的裸机应用程序中,一些中断源是具有相同优先级的4个FPGA中断(比如IRQ ID 58、59、60、61),其思想是所有中断都在运行时连续触发。我可以说,中断处理程序可以限定为长,但不是很长

GIC检测到所有中断都会触发,并且所有中断都被标记为挂起。问题是,只有两个ID较高的中断(58,59)由CPU处理,使其他两个中断处于饥饿状态。一旦58或59完成,它们的源代码将再次触发,并一次又一次地抓取CPU。我的其他中断被无限期地饿死了

我玩弄优先级,给60和61分配更高的中断。果不其然,60和61被触发并由CPU处理,但58和59被饿死。所以这真的是一个饥饿的问题


有什么办法可以解决这个问题吗?如果GIC实现是ARM的设计之一,那么相同优先级的多个中断的仲裁方案固定为“调度编号最低的中断”,所以,如果你希望它能变成某种循环计划,那你可能是运气不好

这就是说,如果这些中断或多或少是永久性的,并且您将它们背靠背地处理,那么这表明您可能不需要使用中断,或者至少代码的设计是不合适的。根据任务的具体性质,我会考虑以下一些想法:

  • 只需依次在每个设备上运行一个连续的轮询循环。如果有一段时间每个设备可能都不需要维修,而且不容易判断,那么保留一个简单的中断处理程序,它只是自动设置一个标志/序列号等,以通知循环谁准备好了
  • 在一个内核上处理所有中断,在另一个内核上处理实际处理。处理程序只需抓取必要的数据,将其塞入队列,然后尽快返回,而另一个人则在队列中稳步地咀嚼
  • 如果捕获每一个中断比平均获得每一个中断的“足够”重要得多,那么在处理它之后,让每个中断在适当的超时时间内处于禁用状态。或者,通过一次只启用一个循环来修改您自己的循环调度,处理程序将重新启用下一个中断,而不是刚刚执行的中断
在我使用ARM Cortex-A9(带GIC的双核)的裸机应用程序中


有没有办法离开这里,这样其他两个仍然会被处理,因为他们的触发率

当然有很多方法

  • 您有一个双CPU,因此可以将一个集合路由到每个CPU;58/59至CPU0,60/61至CPU1。现在还不清楚您是如何使用分发服务器或每CPU接口处理事情的
  • 第二种方法是只读取60/61的58/59处理程序中的状态并执行工作。也就是说,您始终可以从IRQ处理程序读取另一个中断的状态
  • 您还可以在确认原始源之前,为IRQ开始时记录的每个挂起中断提供服务。在IRQ控制器层实现的“2”的变体
  • 我认为,这些解决方案中的大多数都避免了不必要的上下文保存/恢复,而且应该更加高效

    当然,如果你要求CPU做的工作比它能处理的更多,优先级并不重要。问题可能是您的代码效率不高;裸机中断基础设施或FPGA IRQ处理程序。FPGA到CPU的接口也很可能设计得不好。您可能需要在FPGA中添加FIFO来缓冲数据,以便CPU一次可以处理更多数据。我曾与几位FPGA设计师合作过。他们有很大的灵活性,通常如果您要求一些可以使IRQ处理程序更高效的东西,他们可以实现它