My interrupt system
Posted: Tue Mar 25, 2003 10:27 am
My interrupt system is like this:
I have an IDT of 48 entries (32 exceptions and the next 16 are the remapped IRQs). All of these descriptors point to their own piece of code which does the following. If the interrupt pushes NO error code on the stack, an error code of 0 is pushed on the stack and then the interrupt number is pushed on the stack, it then jumps to the global interrupt handler (GIH from now on). For exceptions which do have their own error code, only the extra interrupt number is pushed on the stack and the code jumps to the GIH. Only the double fault handler works different, it uses a Task descriptor and how that works is unimportant right now.
When the GIH gets control it saves all registers and then checks the interrupt number. It has a list somewhere in memory with the interrupt handler for each interrupt (only 1 interrupt handlers per interrupt), this interrupt handler gets the error code as a parameter. If the interrupt handler is a NULL value, nothing is done. This piece of code works the same for all 48 interrupts. After the interrupt handler gives control back to the GIH, the GIH checks if the interrupt handler is above 31 (an IRQ), it then sends the EOI to the PIC (and also an EOI to the slave pic if the IRQ is above 7).
This is actually very basic ideas and I think this is used by more system (Tim's Mobius does it like this if I'm right, and Newos too). But there are some things I might change. Is the list with interrupt handlers the GIH uses with only 1 pointer to an interrupt handler enough (and that the interrupt handler itself can share it with other handling code), or should it be able to register a max of 4 or 8 interrupt handlers per interrupt in the GIH? I think the first option is the best, since for the exceptions, only one handler is enough.
If I do make it possible to register more interrupt handlers per interrupt in the GIH, I think it's better to use 2 GIHs. One for the first 32 exceptions (which will only have one interrupt handler in their GIH) and one for the next 16 IRQs (which will have multiple interrupt handlers registered in the GIH).
The other question I have is if I should directly implement some code inside the GIH that runs the task sheduler, besides the the interrupt handler which can be registered with the interrupt. The task sheduler is one of the very core parts of the system and I think it deserves to be baked inside the GIH itself.
Now I would like to know what you think of my idea. Do you have any comments or anything else to say? How does your interrupt system works? I'd like to know more about anybody else's interrupt system, let me know.
I have an IDT of 48 entries (32 exceptions and the next 16 are the remapped IRQs). All of these descriptors point to their own piece of code which does the following. If the interrupt pushes NO error code on the stack, an error code of 0 is pushed on the stack and then the interrupt number is pushed on the stack, it then jumps to the global interrupt handler (GIH from now on). For exceptions which do have their own error code, only the extra interrupt number is pushed on the stack and the code jumps to the GIH. Only the double fault handler works different, it uses a Task descriptor and how that works is unimportant right now.
When the GIH gets control it saves all registers and then checks the interrupt number. It has a list somewhere in memory with the interrupt handler for each interrupt (only 1 interrupt handlers per interrupt), this interrupt handler gets the error code as a parameter. If the interrupt handler is a NULL value, nothing is done. This piece of code works the same for all 48 interrupts. After the interrupt handler gives control back to the GIH, the GIH checks if the interrupt handler is above 31 (an IRQ), it then sends the EOI to the PIC (and also an EOI to the slave pic if the IRQ is above 7).
This is actually very basic ideas and I think this is used by more system (Tim's Mobius does it like this if I'm right, and Newos too). But there are some things I might change. Is the list with interrupt handlers the GIH uses with only 1 pointer to an interrupt handler enough (and that the interrupt handler itself can share it with other handling code), or should it be able to register a max of 4 or 8 interrupt handlers per interrupt in the GIH? I think the first option is the best, since for the exceptions, only one handler is enough.
If I do make it possible to register more interrupt handlers per interrupt in the GIH, I think it's better to use 2 GIHs. One for the first 32 exceptions (which will only have one interrupt handler in their GIH) and one for the next 16 IRQs (which will have multiple interrupt handlers registered in the GIH).
The other question I have is if I should directly implement some code inside the GIH that runs the task sheduler, besides the the interrupt handler which can be registered with the interrupt. The task sheduler is one of the very core parts of the system and I think it deserves to be baked inside the GIH itself.
Now I would like to know what you think of my idea. Do you have any comments or anything else to say? How does your interrupt system works? I'd like to know more about anybody else's interrupt system, let me know.