From owner-freebsd-arch Thu Jan 10 0:57:54 2002 Delivered-To: freebsd-arch@freebsd.org Received: from rwcrmhc51.attbi.com (rwcrmhc51.attbi.com [204.127.198.38]) by hub.freebsd.org (Postfix) with ESMTP id 94BFE37B421 for ; Thu, 10 Jan 2002 00:57:44 -0800 (PST) Received: from peter3.wemm.org ([12.232.27.13]) by rwcrmhc51.attbi.com (InterMail vM.4.01.03.27 201-229-121-127-20010626) with ESMTP id <20020110085739.EBCO288.rwcrmhc51.attbi.com@peter3.wemm.org> for ; Thu, 10 Jan 2002 08:57:39 +0000 Received: from overcee.netplex.com.au (overcee.wemm.org [10.0.0.3]) by peter3.wemm.org (8.11.0/8.11.0) with ESMTP id g0A8vcs60456 for ; Thu, 10 Jan 2002 00:57:38 -0800 (PST) (envelope-from peter@wemm.org) Received: from wemm.org (localhost [127.0.0.1]) by overcee.netplex.com.au (Postfix) with ESMTP id AC1D538CC; Thu, 10 Jan 2002 00:57:38 -0800 (PST) (envelope-from peter@wemm.org) X-Mailer: exmh version 2.5 07/13/2001 with nmh-1.0.4 To: Dan Eischen Cc: Archie Cobbs , Alfred Perlstein , arch@FreeBSD.ORG Subject: Re: Request for review: getcontext, setcontext, etc In-Reply-To: <3C390746.5FE7648C@vigrid.com> Date: Thu, 10 Jan 2002 00:57:38 -0800 From: Peter Wemm Message-Id: <20020110085738.AC1D538CC@overcee.netplex.com.au> Sender: owner-freebsd-arch@FreeBSD.ORG Precedence: bulk List-ID: List-Archive: (Web Archive) List-Help: (List Instructions) List-Subscribe: List-Unsubscribe: X-Loop: FreeBSD.ORG Dan Eischen wrote: > Peter Wemm wrote: > > > > Archie Cobbs wrote: > > > Alfred Perlstein writes: > > > > > Is there a reason that getcontext and setcontext need to be > > > > > system calls? > > > > > > > > Atomicity? > > > > > > That can't be why.. otherwise this would imply that just because > > > something is written in assembly instead of C that it could have > > > atomicity problems. > > > > Well, consider that setjmp()/longjmp() have embedded system calls (ie: > > sigprocmask).. SVR4 (ie: including Solaris) use setcontext etc to return > > from signals and it needs to restore the signal masks etc. The posted > > patches also have sigprocmask(2) syscalls in the get/setcontext > > implementations. Since it is going to make a syscall anyway, why not push > > it all to a syscall? > > It's not a syscall in the threads library since these functions use > _sigprocmask (not __sys_sigprocmask), and the threads library overrides > the weak definition of it in libc with a strong definition in libc_r. > It has to do this because the signal mask is on a per-thread basis and > the kernel only knows about the process signal mask. Who said that get/set/swapcontext() had to be used with libc_r with a userland reimplementation of sigprocmask? > > It would also allow you to return to a VM86 context. > > The context argument passed in to signal handlers should be able to be used > > with setcontext() to return from the signal handler as an alternative to > > sigreturn(). Doing it in libc wont work there because you race with > > restoring the signal mask before you've finished setting the application > > state. > > Yes, it will. We know when a signal occurs, and we manually restore > the process signal mask in the signal handler. Not when you use get/set/swapcontext() in non-libc_r apps. > > Also, I noticed that the i386 patch doesn't save FP state (!) which is > > one of the primary reasons for get/setcontext(). I'm not sure if this > > can be efficiently done since this user-level function will not know if > > the current context has touched the FPU yet.. > > Neither does the kernel, does it? I thought I saw comments in the > kernel (was it alpha?) about it being too bad that we couldn't tell > if the FPU was used. In libc_r, we currently only save and restore the > FP state when the context is generated from a signal handler (or perhaps > in the case of KSEs, when the thread was preempted). If the context > were from library thread switches, we assume the FP state is no longer > needed since the application made a library call and hit a blocking or > yielding condition. Yes, the kernel does know. When a process accesses the fpu (even to save or restore its context), it traps into the kernel and the npx device assigns the fpu to the process. > > eg, the kernel can do this in getcontext: > > /* save machine state */ > > getgregs(p, ucp->uc_mcontext.gregs); > > /* If we are using the floating point unit, save state */ > > if (p->p_pcb.pcb_fpu.fpu_flags & FPU_EN) > > getfpregs(p, &ucp->uc_mcontext.fpregs); > > else > > ucp->uc_flags &= ~UC_FPU; > > Secondly, it may be that the process has got a saved fp state, but it may > > not be loaded into the FPU registers.. It may be stashed in pcb_fpusave > > still and waiting for the first reference to fault into the kernel so that > > it can load them into the fpu registers again. If the context save was don e > > in the kernel then it could copy the fpu registers from the pcb if that is > > their current official location. > > > > Solaris seems to have getsetcontext(int cmd, ucontext_t *ucp), where > > cmd == GETCONTEXT, SETCONTEXT etc. I think they use this as a helper for > > the library routines. They'd call that instead of sigprocmask() and manual ly > > saving the regsters. The libc functions would probably deal with the link > > stuff. > > > > BTW2; the i386 implementation doesn't have the full FPU state.. ie: no > > SSE or SSE2 context. It should be using fxsave/fxrstor if present, which > > is an additional reason to do this in the kernel. > > I don't think that what's currently implemented for i386 is any > different than setjmp/longjmp, and libc_r has been using those since > the beginning without any problems. It does save the FP state when it > gets a signal and restores it when resuming a thread interrupted by a > signal (like I mentioned above). setjmp/longjmp work standalone without depending on userland libc_r wrappers. Your implementation of get/set/swapcontext() cannot if there is a pending signal involved. > > BTW3; the ia64 has got some "interesting" handling required here. Having > > libc_r use these new functions means that libc_r will be a step closer > > to working on ia64. I suspect that fpu state handling on the ia64 will > > require a syscall to do it efficiently. > > I'd like to avoid the overhead of a syscall to switch threads if > at all possible. You may have no choice. The jury is out there for the moment though. Cheers, -Peter -- Peter Wemm - peter@FreeBSD.org; peter@yahoo-inc.com; peter@netplex.com.au "All of this is for nothing if we don't go to the stars" - JMS/B5 To Unsubscribe: send mail to majordomo@FreeBSD.org with "unsubscribe freebsd-arch" in the body of the message