Hello all!

I have some simple questions about interrupts on x86.


1. Interrupt vectors 0-31 are reserved by Intel. Are they reserved only in PM? I am asking because I am wondering -- we have interrupts 0x13, 0x10, etc for example, but in real mode.

2. If we executed 'cli' command, how will behave interrupts, issued this time (till 'sti')? Will they lost? I know about how NMI works in this case, but not about usual INTs...

3. As I understood, a device issue a signal to interrupt ontroller, and IC transfers it to CPU's. After this CPU requests (IC?) for interrupt's vector. A device must answer this request with a byte, containing vector. Is it right scheme? If yes, is there a standart, which determines which concrete number a concrete device must issue? For example, a HDD must answer with 0x13.

4. As I know, in BIOS it is possible to assign interrupt's handlers (I mean non-PNP devices) to vector's numbers. What does it mean? Is it explanation for 3rd question?

TIA and sorry for my English :).
Posted on 2006-05-27 16:48:28 by Mika0x65
1. BIOS handlers distinguish (at least they are supposed to) between the two.
2. They're masked - not lost (they're held inside the IRR of the Local APIC). If not handled quickly, any next interrupt on the same vector is 'lost'. For example: if you get int at vector 30h, while it's masked, nothing happens. Any next int at vector 30h is 'lost'. You normally don't clear the IF flag for too long. Local APIC is supposed to be able to 'buffer' 2 interrupts (with the help of the ISR: The first interrupt is held inside the IRR, normally, and the second one iside the ISR, exceptionally).
3. It depends on wheter you run in 'compatibility' (or 'PIC') mode, or in SIO mode (using the IO APIC). Every modern machine has an APIC which starts in PIC mode (of course it may start in SIO mode - it's BIOS-specific). There's also a 'virtual wire mode'.
4. Please read about the IO APIC and Local APIC (not ACPI, which is completely different thing). Devices (like PCI devices, ATAs, FDCs, etc.) are physically connected to IOAPIC's input pins. You have to know your chipset, or use any other way to learn how they're connected (you can use ACPI , or Multiprocessor Specification Tables). Normally: PIT is connected to input pin 0, FDC is connected to input pin 6, etc. But you can't rely on that, because it's chipset-dependent. When the IOAPIC receives an interrupt at one of its input pins, it sends an interrupt to the CPU's Local APIC (LAPIC). The LAPIC sends it (or not) to the CPU's core for handling.

Here's how it works:
> Image <
1. An interrupt is sent to IOAPIC (or to 8259A PIC which is emulated by the IOAPIC in compatibility mode).
2. Then the interrupt is sent to the LAPIC
3. Then to the CPU's core.

I don't know how exactly the PIC runs (because it's a quite outdated piece of junk :P ), so it may be different from what I've written.
And I may be wrong here or there, because I'm in the middle of studying the IOAPIC-LAPIC interrupts myself :mrgreen:
Posted on 2006-05-27 18:17:34 by ti_mo_n
I happen to like outdated junk :)
Posted on 2006-05-28 02:38:25 by Homer
Well, what I can conclude for now:

1. Vector's numbers, used in RM and PM by BIOS to handle interrupt requests are different. It means that they work both in PM and RM (I am happy! :) )

2. Simplifying what you said, is it possible to use the following scheme:

1. An interrupt X issued to CPU, handler is running, INTR interrupts are disabled.
2. A next interrupt X issued by hardware, is held somewhere (for now it doesn't matter where exactly)
3. An interrupt Y issued by hardware, held.
4. An interrupt X issued by hardware, lost.
5. An interrupt Y issued by hardware, lost.

?

3. Well, I feel that this is a big theme. I have to read it by myself.

4. I meant something another. For example, I have a card (non-PNP). In its manual said, that it uses interrupt N 12, for example. In BIOS I have to set up int12 to this type of cards (sound, network, etc). Does it mean, that this card will always issue number 12 while answering to APIC "who send an interrupt to me" request? Unfortunately, I haven't such devices, so I can't to test it :(.


Anyway, I feel that interrupts handling is a very big theme. Can you advise me good, comprehensive material about it?

TIA, Mikae.
Posted on 2006-05-28 04:09:27 by Mika0x65
1. Only the so called "Advanced" BIOSes can service interrupts while in proteced mode. It's a rather useless feature, so I don't know whether it's widely supported, or not. I have 3 intel-chipset machines (1 for Celerons, 1 for PIIIs and 1 for P4s) and neither of them supports servicing INTs while in protected mode.

2. Exactly, except pont5: Int Y will be 'held' (you can buffer 2 of each interrupt vectors).

4. As I've siad - I'm not a big fan of outdated junk :P So I don't know how to support non-PNP devices. In my OS, I'm not going to support such devices at all. Since every device must be physically 'hardwired' to some IOAPIC's input pin, then I guess that you have to read chipset's manuals to find out which device port is connected where. I haven't studied anything besides PCI architecture, yet, so I may be completely wrong here.

Please Read:
- IO APIC (including the update)
- Intel's IA-32 Manuals (3 books in 6 PDFs + optimization guide [1 PDF] )
- Multiprocessor Specification v1.4 (May 1997) <-- This one explains a lot about the IOAPIC itself.
- Using the IO APIC. Step by step.
Posted on 2006-05-28 17:28:49 by ti_mo_n

1. Only the so called "Advanced" BIOSes can service interrupts while in proteced mode. It's a rather useless feature, so I don't know whether it's widely supported, or not. I have 3 intel-chipset machines (1 for Celerons, 1 for PIIIs and 1 for P4s) and neither of them supports servicing INTs while in protected mode.

AFAIK only machines designed for OS/2 had these "advanced BIOSes".
Posted on 2006-05-29 08:22:50 by f0dder
ti_mo_n, thx for links!

Well, I've read more about interrupts and I have new questions :).

1. As I understood, if CPU will get more than one int at the same time it will "forget" all ints caused by software (int instructions, faults, traps) and serve all hardware interrupts. When execution will continue, all faults will be raised again. Is it right?

2. I didn't understood, how processor will behave itself, in the case when it receives an interrupt number which exceeds limit field in IDT. Will it stop, waiting for NMI or reset, or GP will be generated?

TIA, and sorry for my English :).
Posted on 2006-05-30 06:31:36 by Mika0x65
#2: double fault? triple fault? it's probably mentioned in the intel "system programming" docs, but I have to move some stuff around now, so can't check for you =)
Posted on 2006-05-30 07:10:53 by f0dder
1. Software INT instruction (or INT3, or INTO with O flag set) immidiately breaks the execution and jumps to the handler's routine (WITHOUT pushing any error code, so be careful, because your handler may assume that there IS an error code on the stack, which will most likely end with triple fault :) ). It's much like a 'call'. Actually, it's being used in linux API, iirc (INT 080h). Software INTs don't have anything to do with IO APIC, LOCAL APIC, or interrupt buffering. They just get the handler routine's entry-point from the IDT (and optionally GDT/LDT, depending on the design) and jump (or more like 'call') to it, if possible.

2. It will cause GPF (iirc), which can cause double fault, which can cause triple fault. :) Yes, it's in the Intel's manuals (volume 3, chapter "interrupt handling", iirc). #GP (a.k.a GPF) is raised every time the protection (esp. the memory protection) is breached.
Posted on 2006-05-30 13:51:18 by ti_mo_n
ti_mo_n,

1. No, I just wanted to ask, about order of interrupts and exceptions handling issued at the same time :).

Already 2 men said 'triple fault' :). How it is possible? As I understood double fault happens when CPU raises exeption while it is TRYING to switch to exception handler of the same type.  Also, double fault will be raised if TS exception occurs while RUNNING an exception handler (Interesting, why Intel implemented such behavior?..). In this cases it will stop execution till NMI or reset. So, where is a place for 3rd fault?..
Posted on 2006-05-31 07:50:00 by Mika0x65
Woops. I think I understood how triple fault possible. For example, we have IDT with 0 limit. Very stupidly, but :)... Suddenly we've got an GP fault. This fault will raise a new one GP fault. This is double fault and it will raise a new one, third fault (Not fault, but 'crash'?.. Don't know how it will be in English), after which processor will stop.

Anyway, two faults is enough to stop execution...

Fufff! It is not so easy! :)
Posted on 2006-05-31 17:09:43 by Mika0x65
There are no answers... I said dumb thing?..
Posted on 2006-06-01 09:58:47 by Mika0x65
Or perhaps a correct thing :)

A triple fault (or, in reality, a hard-reset) happens if the CPU gets an exception while trying to process the handler for a double-fault.

Your idt-limit-0 sounds like one example where this could happen, an IDT with invalid handler entries probably could too, and something as silly as gp-fault handler accessing non-available memory probably could too. Consult the intel "system programming" docs :)
Posted on 2006-06-01 11:10:37 by f0dder
Thank you all for answers :).

One more question, please:

I read, that interrupts and also EXCEPTIONS have priorities. And I feel a bit confused about it.  Priorities, listed in my book, look like this:

1. Traps (trapped by T flag in TSS, TF, code breakpoints).
2. Traps (data breakpoints).
3. NMI.
4. INT.
5. NP# while CPU is fetching next instruction.
6. Wrong opcode.
7. Some FPU exceptions.
8. NP, GPF.
9. Alignment exceptions
10. Page not present.

I can imaging myself a situation, when interrput and exception occure at the same time. But how can two exception occure in this way?.. Not one by one, but in the same time!

I have only one assumption. For example, NP for stack segment occures. At this time CPU is trying to fetch a new one instruction and finds, that a page with this instruction not present.

But I'm not sure about these scheme. Can someone (f0dder, ti_mo_n? :) ) tell me, is it right?

TIA, Mikae.
Posted on 2006-06-08 12:29:55 by Mika0x65
I never really boggled my mind with exception priorities, so I can't help there. I don't know if it's much of an issue, anyway, with a well-designed and pre-emptive kernel.
Posted on 2006-06-08 12:37:59 by f0dder
It's a pitty. I understand it is not so important, but I am trying to know as much as possible.
Posted on 2006-06-08 13:03:49 by Mika0x65
Hopefully somebody else has studied it more than I have... otherwise, I guess you'll have to dig into the pretty heavy intel manuals :)
Posted on 2006-06-08 13:22:09 by f0dder
Well, I've got hardcopies of Intel's manuals and now I have answer to my question, I think.

May be, it will be usefull for somebody.

Yes, really exceptions and interrupts have priorities. Certainly, not every exceptions may occur at the same time with any other, but, for example GPF and INT 1 can. More interesting thing (at least, for me :) ) is that page fault for code can occur simultaneously with any other exception because of CPU prefetches instructions from memory.
Posted on 2006-06-15 19:09:15 by Mika0x65
The following applies to 'SM' IOAPIC mode. I don't know how any other mode works.

So:

When 2 interrutps occur at the same time, interrutp arbiter chooses 1 of them based on their priority, and sends it to proper CPU (the proper one is the one perviously programmed using some registers inside the IOAPIC and some registers inside the CPU's LAPIC).

After this, any next interrutps is sent.

This way interrutps get delivered to CPUs' LAPICs based on their priority. CPUs handle them based on THEIR OWN (CPUs') internal priorities (which may differ). So you can get interrupt1, interrupt3, interrupt5 (according to the IOAPIC's priorities), but they will be handled in the following order:

interrupt1 fires int60h and is serviced.
interrupt3 gets queued as int80h, while int60h is being serviced.
interrupt5 gets queued as int70h, while int60h is being serviced.
int70 is being serviced. (interrupt5)
int80 is being serviced. (interrupt3)

This is just an example. Everything can be programmed using the IOAPIC.

Exceptions are hardcoded inside the CPU to have lowest indices (highest priorities), so they take precedence before any interrupts.

Priorities of every individual exception are inside intel's manuals. Priorities of individual interrupts are programmed by software, but they're always lower (higher indices) than exceptions.

NMI interrupt is an exception within exceptions, because it's hardcoded to have very low index (very high priority). It's described inside the manuals.
Posted on 2006-06-15 19:54:38 by ti_mo_n