Can an interrupt handler be preempted by the same interrupt handler?

混江龙づ霸主 提交于 2019-11-27 15:15:50

问题


Does the CPU disable all interrupts on local CPU before calling the interrupt handler? Or does it only disable that particular interrupt line, which is being served?


回答1:


x86 disables all local interrupts (except NMI of course) before jumping to the interrupt vector. Linux normally masks the specific interrupt and re-enables the rest of the interrupts (which aren't masked), unless a specific flags is passed to the interrupt handler registration.

Note that while this means your interrupt handler will not race with itself on the same CPU, it can and will race with itself running on other CPUs in an SMP / SMT system.




回答2:


Normally (at least in x86), an interrupt disables interrupts.

When an interrupt is received, the hardware does these things:
1. Save all registers in a predetermined place.
2. Set the instruction pointer (AKA program counter) to the interrupt handler's address.
3. Set the register that controls interrupts to a value that disables all (or most) interrupts. This prevents another interrupt from interrupting this one.

An exception is NMI (non maskable interrupt) which can't be disabled.




回答3:


Yes, that's fine. I'd like to also add what I think might be relevant.

In many real-world drivers/kernel code, "bottom-half" (bh) handlers are used pretty often- tasklets, softirqs. These bh's run in interrupt context and can run in parallel with their top-half (th) handlers on SMP (esp softirq's).

Of course, recently there's a move (mainly code migrated from the PREEMPT_RT project) towards mainline, that essentially gets rid of the 'bh' mechanism- all interrupt handlers will run with all interrupts disabled. Not only that, handlers are (can be) converted to kernel threads- these are the so-called "threaded" interrupt handlers.

As of today, the choice is still left to the developer- you can use the 'traditional' th/bh style or the threaded style.

Ref and Details:

http://lwn.net/Articles/380931/

http://lwn.net/Articles/302043/




回答4:


Quoting Intels own, surprisingly well-written "Intel® 64 and IA-32 Architectures Software Developer’s Manual", Volume 1, pages 6-10:

If an interrupt or exception handler is called through an interrupt gate, the processor clears the interrupt enable (IF) flag in the EFLAGS register to prevent subsequent interrupts from interfering with the execution of the handler. When a handler is called through a trap gate, the state of the IF flag is not changed.

So just to be clear - yes, effectively the CPU "disables" all interrupts before calling the interrupt handler. Properly described, the processor simply triggers a flag which makes it ignore all interrupt requests. Except probably non-maskable interrupts and/or its own software exceptions (please someone correct me on this, not verified).




回答5:


We want ISR to be atomic and no one should be able to preempt the ISR.

Therefore, An ISR disables the local interrupts ( i.e. the interrupt on the current processor) and once the ISR calls ret_from_intr() function ( i.e. we have finished the ISR) , interrupts are again enabled on the current processor.

If an interrupt occurs, it will now be served by the other processor ( in SMP system) and ISR related to that interrupt will start running.

In SMP system , We also need to include the proper synchronization mechanism ( spin lock) in an ISR.



来源:https://stackoverflow.com/questions/11403915/can-an-interrupt-handler-be-preempted-by-the-same-interrupt-handler

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!