TSS and SS0, ESP0....

Question about which tools to use, bugs, the best way to implement a function, etc should go here. Don't forget to see if your question is answered in the wiki first! When in doubt post here.
User avatar
iocoder
Member
Member
Posts: 208
Joined: Sun Oct 18, 2009 5:47 pm
Libera.chat IRC: iocoder
Location: Alexandria, Egypt | Ottawa, Canada
Contact:

TSS and SS0, ESP0....

Post by iocoder »

Hi guys...
One advantage of TSS is that it has entries for SS0 [SS for PL0] and ESP0 [ESP for PL0]. this helps me a lot when a ring3 program has a ring 3 to 0 switch. for example, when the ring 3 program do "int $0x80" [syscall], the CPU will change the value in SS to SS0 and ESP to ESP0 automatically, and pushes old SS and old ESP on the new kernel-mode stack....
Quafios [my OS] has been using soft-ware switch for a while and it works well, but i would like to make use of the feature SS0 and ESP0 without moving to hard-ware switch... is there a good idea to do it???? it is necessary because the stack of a ring 3 process is dynamically growing on. when the program needs more, a page fault happens and the CPU pushes values onto the stack that -in fact- needs to grow, then another page fault happens and so on...... :x
If TSS was enabled, and a page fault happened, the CPU would automatically change SS and ESP and push what he wants to push onto the new stack... how flexible!!! any ideas??????

Thanks and Regards,
User avatar
bluemoon
Member
Member
Posts: 1761
Joined: Wed Dec 01, 2010 3:41 am
Location: Hong Kong

Re: TSS and SS0, ESP0....

Post by bluemoon »

On IA32 / IA64 manual, section 5.8.5:
IA manual wrote:5.8.5 Stack Switching
Whenever a call gate is used to transfer program control to a more privileged nonconforming code segment (that is, when the DPL of the nonconforming destination code segment is less than the CPL), the processor automatically switches to the stack for the destination code segment’s privilege level. This stack switching is carried out to prevent more privileged procedures from crashing due to insufficient stack space. It also prevents less privileged procedures from interfering (by accident or intent) with more privileged procedures through a shared stack.

Each task must define up to 4 stacks....<snip>...The operating system is responsible for creating stacks and stack-segment descriptors for all the privilege levels to be used and for loading initial pointers for these stacks into the TSS
This is why you need at least one TSS if you ever want to get from ring3 to ring0.
it is necessary because the stack of a ring 3 process is dynamically growing on. when the program needs more, a page fault happens and the CPU pushes values onto the stack that -in fact- needs to grow, then another page fault happens and so on......
This is not going to happen since you have (and require) an TSS for stack switch from 3 to 0.
User avatar
iocoder
Member
Member
Posts: 208
Joined: Sun Oct 18, 2009 5:47 pm
Libera.chat IRC: iocoder
Location: Alexandria, Egypt | Ottawa, Canada
Contact:

Re: TSS and SS0, ESP0....

Post by iocoder »

thanks a lot, but by loading TR, hardware context switching is enabled, isn't it???
User avatar
bluemoon
Member
Member
Posts: 1761
Joined: Wed Dec 01, 2010 3:41 am
Location: Hong Kong

Re: TSS and SS0, ESP0....

Post by bluemoon »

By loading TR (ie. LTR instruction) itself does not trigger any context switch.

But context switch (going thru' about 12 bullet points of checking and loading) is unavoidable when requesting more more privilege, it is slow but it's a protection measure.

If you don't need such protection you may just run all stuff with same privilege.

ps. The so called "hardware context switch" is always enabled. If you try to get from rin3 to ring0 without a task (previously LTR'ed) you get an CPU exception.
egos
Member
Member
Posts: 612
Joined: Fri Nov 16, 2007 1:59 pm

Re: TSS and SS0, ESP0....

Post by egos »

Hi, mostafazizo.
For handling critical errors such as kernel stack page fault you should use additional TSS(s) in IA-32.
If you have seen bad English in my words, tell me what's wrong, please.
User avatar
iocoder
Member
Member
Posts: 208
Joined: Sun Oct 18, 2009 5:47 pm
Libera.chat IRC: iocoder
Location: Alexandria, Egypt | Ottawa, Canada
Contact:

Re: TSS and SS0, ESP0....

Post by iocoder »

By loading TR (ie. LTR instruction) itself does not trigger any context switch.

But context switch (going thru' about 12 bullet points of checking and loading) is unavoidable when requesting more more privilege, it is slow but it's a protection measure.

If you don't need such protection you may just run all stuff with same privilege.

ps. The so called "hardware context switch" is always enabled. If you try to get from rin3 to ring0 without a task (previously LTR'ed) you get an CPU exception.
Hi, mostafazizo.
For critical errors such as kernel stack page fault you should use additional TSS(s) in IA-32.
thanks guys...
now i believe i have to use at least one TSS... using TSS and loading it to TR will not activate hardware context switching, will it??? to say we are using hardware context switching, we have to do a far jump to TSS selector for each task-switch.. and this is the slow part that modern operating systems don't use... is that right??
User avatar
bluemoon
Member
Member
Posts: 1761
Joined: Wed Dec 01, 2010 3:41 am
Location: Hong Kong

Re: TSS and SS0, ESP0....

Post by bluemoon »

mostafazizo wrote:and this is the slow part that modern operating systems don't use... is that right??
The whole point is avoid context switch if it is not necessary. for example, scheduling between process group which involve no privilege change. However, to get higher privilege it by definition involve a context switch, even for modern OS.
User avatar
xenos
Member
Member
Posts: 1121
Joined: Thu Aug 11, 2005 11:00 pm
Libera.chat IRC: xenos1984
Location: Tartu, Estonia
Contact:

Re: TSS and SS0, ESP0....

Post by xenos »

bluemoon wrote:However, to get higher privilege it by definition involve a context switch, even for modern OS.
No, that's wrong.

Going from ring 3 to ring 0 (through an interrupt or call gate) triggers a stack switch: The new values of SS and ESP are loaded from the SS0 and ESP0 fields of the current TSS. However, this is not a hardware context switch, which would be saving all registers into the current TSS, switching to a new TSS and loading all registers from the new TSS, as caused by a jmp / call to a new TSS.

If you want to have ring 3 code (which you certainly want, since any code running in ring 0 can do anything it wants with the system), you need at least one TSS (one TSS per CPU in multiprocessor systems), which will hold the SS0 / ESP0 for the current task. But you don't need to use hardware task switching. For example, you could do the following to implement a simple software task switching (assuming you do a task switch when the timer IRQ fires):
  • The timer IRQ fires and its IDT entry points to a ring 0 interrupt handler.
  • SS and ESP are loaded from the SS0 and ESP0 fields of the current TSS; the old values are pushed on the ring 0 stack (stack switch).
  • Push all registers on the ring 0 stack. Save a copy of CR3 (if you use paging).
  • Call the scheduler, put the current task in the task queue and get a new task to execute.
  • Change the values of SS and ESP to point to the new task's ring 0 stack.
  • Load all register values (including CR3) from the ring 0 stack of the new task.
  • Do an IRET. This will save SS and ESP in the current (new) task's TSS and get you back to ring 3 - of the new task.
Last edited by xenos on Tue May 24, 2011 9:53 am, edited 1 time in total.
Programmers' Hardware Database // GitHub user: xenos1984; OS project: NOS
User avatar
bluemoon
Member
Member
Posts: 1761
Joined: Wed Dec 01, 2010 3:41 am
Location: Hong Kong

Re: TSS and SS0, ESP0....

Post by bluemoon »

Oh I mixed up the terms on context switch and stack switch, thanks for clarification. Hope I'm not confusing the OP.

By the way I guess you mean CR3(pointer to page directory).
User avatar
xenos
Member
Member
Posts: 1121
Joined: Thu Aug 11, 2005 11:00 pm
Libera.chat IRC: xenos1984
Location: Tartu, Estonia
Contact:

Re: TSS and SS0, ESP0....

Post by xenos »

bluemoon wrote:By the way I guess you mean CR3(pointer to page directory).
Of course, you're right... Thanks for the hint.
Programmers' Hardware Database // GitHub user: xenos1984; OS project: NOS
rdos
Member
Member
Posts: 3310
Joined: Wed Oct 01, 2008 1:55 pm

Re: TSS and SS0, ESP0....

Post by rdos »

I find it awkward to save task state on the stack. Mostly because different processor-modes have different stack-layouts. For instance, a V86 task would save segment registers on the top of the stack. An protected mode application would save SS:ESP on top of the stack. For a kernel-debugger, it is also pretty handy if tasks blocked on exceptions have an memory area with registers that is easy to get to, which a stack frame is not, especially not with different processor-modes being involved. I therefore find it more convinient to actually store task state in the thread-control-block instead of on the stack. And exception-handlers would pop-of the exception handler frames from the stack, and reload the state so the thread points to the faulting instruction, and not code in an exception handler.
rdos
Member
Member
Posts: 3310
Joined: Wed Oct 01, 2008 1:55 pm

Re: TSS and SS0, ESP0....

Post by rdos »

mostafazizo wrote:now i believe i have to use at least one TSS... using TSS and loading it to TR will not activate hardware context switching, will it??? to say we are using hardware context switching, we have to do a far jump to TSS selector for each task-switch.. and this is the slow part that modern operating systems don't use... is that right??
Pretty much, yes. Loading TR is similar to loading a segment register. It does do a few validations, and it sets the TSS to busy, but it doesn't save/load register-state in the TSS.

The reason I use one TSS per thread has to do with IO-permission bitmap. I have tasks that should have no IO-port restrictions, even if they run at ring 3 (the V86 video-mode switcher), and tasks that should be restricted. It is non-trivial to solve this issue with only one TSS per processor. The other issues (setting the correct SS0:ESP0 and possibly CR3) with every task-switch is not a problem really.
User avatar
iocoder
Member
Member
Posts: 208
Joined: Sun Oct 18, 2009 5:47 pm
Libera.chat IRC: iocoder
Location: Alexandria, Egypt | Ottawa, Canada
Contact:

Re: TSS and SS0, ESP0....

Post by iocoder »

thank u guys u r so helpful :)
User avatar
Combuster
Member
Member
Posts: 9301
Joined: Wed Oct 18, 2006 3:45 am
Libera.chat IRC: [com]buster
Location: On the balcony, where I can actually keep 1½m distance
Contact:

Re: TSS and SS0, ESP0....

Post by Combuster »

rdos wrote:It is non-trivial to solve this issue with only one TSS per processor.
Paging works pretty good - you can even have TSSes share bitmaps for free that way. Plus that true threads have the same privileges so in your case you'd have N identical copies of the same bitmap, no?
"Certainly avoid yourself. He is a newbie and might not realize it. You'll hate his code deeply a few years down the road." - Sortie
[ My OS ] [ VDisk/SFS ]
User avatar
xenos
Member
Member
Posts: 1121
Joined: Thu Aug 11, 2005 11:00 pm
Libera.chat IRC: xenos1984
Location: Tartu, Estonia
Contact:

Re: TSS and SS0, ESP0....

Post by xenos »

rdos wrote:I find it awkward to save task state on the stack. Mostly because different processor-modes have different stack-layouts.
Of course, one can also save the register information in a thread control block. As I said, saving them on the stack is only a simple example.
Combuster wrote:
rdos wrote:It is non-trivial to solve this issue with only one TSS per processor.
Paging works pretty good - you can even have TSSes share bitmaps for free that way. Plus that true threads have the same privileges so in your case you'd have N identical copies of the same bitmap, no?
That's indeed very simple, and it's the way I handler IO bitmaps in my kernel. I have one TSS per CPU and one page directory per process (which may contain several threads). IO permissions are granted per process. Thus, every process has its own IO bitmap, which is mapped (via the process' page directory) at the end of the TSS area.
Programmers' Hardware Database // GitHub user: xenos1984; OS project: NOS
Post Reply