seindal@skinfaxe.diku.dk (Rene' Seindal) (03/28/89)
chris@mimsy.UUCP (Chris Torek) writes: > In article <4549@freja.diku.dk> seindal@skinfaxe.diku.dk (Rene' Seindal) writes: > >On 4.3BSD on Vaxen, the struct sigcontext has the same contents as a > >``jmp_buf'' (??), > Not so: > % egrep jmp_buf /usr/include/setjmp.h > typedef int jmp_buf[10]; > % egrep sc\|\{\|\} /sys/h/signal.h > struct sigvec { > }; > struct sigstack { > }; > struct sigcontext { > int sc_onstack; /* sigstack state to restore */ > int sc_mask; /* signal mask to restore */ > int sc_sp; /* sp to restore */ > int sc_fp; /* fp to restore */ > int sc_ap; /* ap to restore */ > int sc_pc; /* pc to restore */ > int sc_ps; /* psl to restore */ > }; > As you can see, sigcontext is not an array of 10 int's. I hate to argue with you. You are right too often :-) I said same contents, not same type. A close look at setjmp will reveal that is only uses the first seven longwords of the jmp_buf, for exactly the values shown above. A comment even says "# construct sigcontext"! jmp_buf is probably only declared as an array, so people don't have to take the address themselves. (I am looking in MORE/bsd sources from Mt. Xinu, marked "@(#)setjmp.s 5.5 (Berkeley) 3/9/86"). > >Even more amusing, the is an undocumented system call (no. 139) in at least > >4.3 (and 4.2) from Berkeley, Ultrix 2.0, and SunOS 3.X (and 4.0, according to > >adb. I haven't tried), which is used by longjmp(3) to restore the saved > >context. It takes a jmp_buf/struct sigcontext as the sole argument. It is a > >kind of simplified sigreturn(2). Don't look in sysent for it, since it will > >probably not be there. > 139 is (was) the `sigcleanup' syscall, used in 4.2BSD to exit from > signal handlers, and indeed undocumented. It did not take *any* > arguments; rather, it found a sigcontext structure via the user stack > pointer pushed by the `chmk' trap, an awful and bloody thing to do, > which is of course why it was fixed in 4.3BSD.... You are right about the argument passing. It does, however, look the same from user code. Code like pushl <addr of sigcontext or a jmp_buf> chmk $139 will do a longjmp (without restoring register contents, as 4.[23] longjmp does). Syscall 139 still exists in the 4.3 I use (MORE/bsd), even though it isn't listed in sysent. Look in the top of syscall(). That is an awful and bloody thing to do too. Was it left in only because of longjmp(), which is able to use sigreturn() instead (more awful and bloody code), or because other programs depended on it (even more awful and bloody)? > I have no idea how SunOS actually handles osigcleanup(). I haven't got sources to SunOS 4.0, but it look like it uses the 4.2 scheme. It has sigcleanup listed as syscall 139 in sysent, taking no arguments. The code for sigcleanup looks similar, fetching a sigcontext pointer from the user stack, followed by a copyin of the necessary parts of the sigcontext, and assignment to the saved registers in the user structure. SunOS hasn't got sigreturn either, so those parts of the kernel might be from 4.2. Rene' Seindal (seindal@diku.dk).
chris@mimsy.UUCP (Chris Torek) (03/30/89)
>>In article <4549@freja.diku.dk> seindal@skinfaxe.diku.dk (Rene' Seindal) wrote: >>>On 4.3BSD on Vaxen, the struct sigcontext has the same contents as a >>>``jmp_buf'' (??), >to which I said >>Not so: In article <4557@freja.diku.dk> seindal@skinfaxe.diku.dk (Rene' Seindal) replies: >I said same contents, not same type. Ah: I misinterpreted. >[setjmp] uses [only] the first seven longwords of the jmp_buf.... Indeed it does. >jmp_buf is probably only declared as an array, so people don't have >to take the address themselves. Historically, jmp_buf has always been an array; and according to the pANS for C, it must be so. In fact the array was once used to hold r6 through r15 (in the days of 4.1BSD), and its size is a holdover. But the two are not interchangeable, aside from an accident of implementation (well, of design, in this case). It is reasonable for setjmp and longjmp to want to preserve more state than a sigcontext (register contents, for instance, on 680x0s, where the call frame does not let you restore registers by unwinding). Sticking with jmp_bufs for longjmp and sigcontexts for signals is much safer. >Syscall 139 still exists in the 4.3 I use (MORE/bsd) ... (and in 4.3tahoe) >Was it left in only because of longjmp() ... or because other >programs depended on it ... ? It was left in for backwards compatibility. 4.3BSD-tahoe will still run most 4.1BSD binaries. (Exceptions are things using the jobs library, and things using vread and/or vwrite. There may be others.) -- In-Real-Life: Chris Torek, Univ of MD Comp Sci Dept (+1 301 454 7163) Domain: chris@mimsy.umd.edu Path: uunet!mimsy!chris
guy@auspex.UUCP (Guy Harris) (03/31/89)
>I said same contents, not same type. A close look at setjmp will reveal that >is only uses the first seven longwords of the jmp_buf, for exactly the values >shown above. A comment even says "# construct sigcontext"! jmp_buf is >probably only declared as an array, so people don't have to take the address >themselves. Well, it's declared as an array because it antedates "struct sigcontext", because it was done that way in good old V7, and because you're supposed to use the name of the "jmp_buf" in calls to "setjmp", which means that, since C generally supports call-by-value, the value had better be a pointer into the "jmp_buf", which means that (unless "setjmp" is a macro - which the dpANS for C says it must be - *and* inserts the "&" for you), "jmp_buf" must be an array (in fact, said dpANS says it's an array). >> 139 is (was) the `sigcleanup' syscall, used in 4.2BSD to exit from >> signal handlers, and indeed undocumented. It did not take *any* >> arguments; rather, it found a sigcontext structure via the user stack >> pointer pushed by the `chmk' trap, an awful and bloody thing to do, >> which is of course why it was fixed in 4.3BSD.... > >You are right about the argument passing. It does, however, look the same >from user code. Code like > > pushl <addr of sigcontext or a jmp_buf> > chmk $139 > >will do a longjmp (without restoring register contents, as 4.[23] >longjmp does). Which isn't quite the same as "finding the structure via the user stack pointer pushed by the 'chmk' trap"; I read that as meaning that no explicit argument is provided, and that the structure is assumed to be at a specific location on the stack. Instead, "syscall 139" *does* take an argument; it just happens to be passed a little differently. Given that neither it nor "sigreturn" are, in general, usable from machine-independent code ("sigreturn" doesn't load up all the registers, which means you need machine-dependent glue around it anyway, if you want something that amounts to a "machine-independent user-mode context switch" call), I don't see this as being particularly awful or bloody. There *was* some problem with the 4.2BSD "syscall 139"; I don't remember what it was, but as I remember it did *not* exist in the SunOS "syscall 139". >Syscall 139 still exists in the 4.3 I use (MORE/bsd), even though it isn't >listed in sysent. Look in the top of syscall(). That is an awful and bloody >thing to do too. Was it left in only because of longjmp(), which is able to >use sigreturn() instead (more awful and bloody code), or because other >programs depended on it (even more awful and bloody)? "longjmp" in 4.3 *does* use "sigreturn". I presume it was left in so that 4.2BSD binaries would continue to run. >I haven't got sources to SunOS 4.0, but it look like it uses the 4.2 scheme. >It has sigcleanup listed as syscall 139 in sysent, taking no arguments. The >code for sigcleanup looks similar, fetching a sigcontext pointer from the user >stack, followed by a copyin of the necessary parts of the sigcontext, and >assignment to the saved registers in the user structure. SunOS hasn't got >sigreturn either, so those parts of the kernel might be from 4.2. SunOS doesn't have "sigreturn" because it didn't need it; as indicated, "sigreturn" isn't a machine-independent interface to a general "context switch" function, and since making such a function out of "sigreturn" would require additional machine-language glue to load up the other registers anyway, it wasn't deemed worth adding as a "real" system call. That part of the kernel isn't from 4.2, though, except on those versions of SunOS 3.0 ported to the VAX - neither VAX nor Tahoe code works as is on the 68K, the 80386, or the SPARC....