patch for %gs saving

Daniel Eischen eischen at pcnet1.pcnet.com
Fri Apr 11 05:43:22 PDT 2003


On Thu, 10 Apr 2003, Julian Elischer wrote:
> 
> On Fri, 11 Apr 2003, Daniel Eischen wrote:
> 
> > On Thu, 10 Apr 2003, Peter Wemm wrote:
> > 
> > > "David Xu" wrote:
> > > > Here is the patch for kernel to save %gs,
> > > > it works well on my machine.
> > > > http://people.freebsd.org/~davidxu/i386_gs.diff
> > > > Daniel, is this the reason in your libpthread
> > > > patch that doesn't use getcontext syscall ?
> > > 
> > > To put some background on the issue, there is a reason why we did not
> > > do this.  %gs is not used by the kernel, so it does not normally need to
> > > be saved and restored on every trap into the kernel.  Setting a segment
> > > register is Really Slow - measured in hundreds of clock cycles.
> > > 
> > > So, we normally only touch %gs when we context switch to a different process
> > > that may have a different %gs.  Or when one of the context syscalls wants
> > > it changed.  We cannot avoid touching %fs because we use it for kernel
> > > private data.  But if it wasn't for that, we wouldn't be touching
> > > %fs for regular traps/syscalls/etc either.
> > > 
> > > Bruce Evans understands this better than I do, I would suggest not making
> > > this change without talking about it with him first.
> > 
> > BTW, it's not really a big deal for the UTS to restore %gs
> > (or probably whatever it ends up being on other archs) before
> > continuing a thread.
> 
> I put it to you that %gs should be a way of finding the current KSE
> mailbox

It is already.

> (upcall mailbox) which will NOT CHANGE when a thread is changed in
> userland. one simply changes the curthread pointer in the KSE (upcall)
> mailbox, leaving %gs the same.
> 
> %gs should never change for a single KSE as it goes in and out of the
> kernel, it must always have the same mailbox.

The problem is switching a thread _between_ KSEs.  If there are
multiple KSEs in a KSEG, then threads can be migrated between
those KSEs by the UTS.  When a thread blocks in the kernel and
then completes, there is no guarantee that the completion upcall
will occur on the same KSE in which the thread was running when
it blocked.  Right now, there is one scheduling queue for each
KSEG (in the UTS), so there is currently no notion of binding
threads to specific KSEs within a KSEG.  If we want to bind
threads to specific KSEs, then we need some sort of load
balancing in the UTS and then still need the ability to
migrate threads.

If you continue a thread on another KSE, then you have to adjust
it's %gs.  And this gets a bit more complicated when you think
about signal handlers and the fact that %gs is in the interrupted
context that gets passed to the signal handler (which the application
can use to setcontext() to).

-- 
Dan Eischen



More information about the freebsd-threads mailing list