I don't understand how the IDT and the TSS fit together with system calls. The wiki suggests that a TSS is necessary for system calls and that the only values in the TSS I have to worry about are SS0, ESP0, and IOPB [1]. I'm assuming -- for lack of better information -- that an i386 Task Gate is used for handling syscalls, which mentions a TSS segment descriptor. However, according to the wiki, the Task Gate type does not use the offset fields [2]. Between these sources, I am unsure of how to set the interrupt handler using these methods. My guess would be set EIP in the TSS, and reset it every time a syscall is handled, but I find it strange that it's not mentioned in the wiki.
Could someone kindly clear this up for me? How am I "supposed" to handle syscalls? What gate type do I use in my IDT? etc. Thanks in advance!
1 http://wiki.osdev.org/Task_State_Segmen ... ltitasking
2 http://wiki.osdev.org/IDT#I386_Task_Gate
Syscalls, IDT, and TSS
Re: Syscalls, IDT, and TSS
Hi,
For hardware task switching (where you're switching from one task to a complete different task and not switching privilege levels within the same task) the SS0 and ESP0 fields aren't used. In this case everything gets loaded from the TSS's normal fields, including ESP being loaded from the "ESP" field (and not the "ESP0" field).
Cheers,
Brendan
Usually when the CPU switches from a less privileged level (e.g. CPL=3) to a more privileged level (e.g. CPL=0) it changes stack, so that the more privileged code doesn't (temporarily) have to use the less privileged code's "untrusted" stack. The details for the new stack come from the TSS (e.g. the SS0 and ESP0 fields).Izzette wrote:I don't understand how the IDT and the TSS fit together with system calls. The wiki suggests that a TSS is necessary for system calls and that the only values in the TSS I have to worry about are SS0, ESP0, and IOPB [1].
For hardware task switching (where you're switching from one task to a complete different task and not switching privilege levels within the same task) the SS0 and ESP0 fields aren't used. In this case everything gets loaded from the TSS's normal fields, including ESP being loaded from the "ESP" field (and not the "ESP0" field).
For syscalls, you probably don't want to do a software task switch or a hardware task switch (and only want to change privilege level), so you don't want a task gate. For software interrupts you'd want to use an interrupt gate or trap gate (depending on whether you want IRQs to be disabled by CPU before starting the syscall handling code).Izzette wrote:Could someone kindly clear this up for me? How am I "supposed" to handle syscalls? What gate type do I use in my IDT? etc. Thanks in advance!
Cheers,
Brendan
For all things; perfection is, and will always remain, impossible to achieve in practice. However; by striving for perfection we create things that are as perfect as practically possible. Let the pursuit of perfection be our guide.
Re: Syscalls, IDT, and TSS
That clears up some things, like how I choose my interrupt handler. But how then does the CPU "choose" the TSS to use? Just the first TSS in the GDT? I don't see how that could work with SMP.
Re: Syscalls, IDT, and TSS
Hi,
For multi-CPU, for "software task switching only" each CPU has its own TSS, for "mostly software task switching but with a few hardware tasks for special purposes like double fault exception handler" each CPU might be given 2 or more TSSs (e.g. one for normal use plus one for double fault), and for "hardware task switching only" the OS might have a few special TSS for special things (double fault) and would ensure that a normal task can't be running on more than one CPU at a time (which is something an OS has to do anyway).
Note that there are no OSs that use "hardware task switching only" anymore - it's slow and pointless (and not portable, not even to 64-bit 80x86).
Cheers,
Brendan
An OS uses the "LTR" instruction to set the current TSS (for each CPU) during boot; then the TSS either never changes afterwards (OS uses software task switching only), or it's changed when software uses a task gate (and CPU knows which TSS to use from the task gate that software used).Izzette wrote:That clears up some things, like how I choose my interrupt handler. But how then does the CPU "choose" the TSS to use? Just the first TSS in the GDT? I don't see how that could work with SMP.
For multi-CPU, for "software task switching only" each CPU has its own TSS, for "mostly software task switching but with a few hardware tasks for special purposes like double fault exception handler" each CPU might be given 2 or more TSSs (e.g. one for normal use plus one for double fault), and for "hardware task switching only" the OS might have a few special TSS for special things (double fault) and would ensure that a normal task can't be running on more than one CPU at a time (which is something an OS has to do anyway).
Note that there are no OSs that use "hardware task switching only" anymore - it's slow and pointless (and not portable, not even to 64-bit 80x86).
Cheers,
Brendan
For all things; perfection is, and will always remain, impossible to achieve in practice. However; by striving for perfection we create things that are as perfect as practically possible. Let the pursuit of perfection be our guide.
Re: Syscalls, IDT, and TSS
That's what I was missing.
Thank you, Brendan!
Thank you, Brendan!