fix(setjmp): restore caller rbx in sigsetjmp mask path
This commit is contained in:
@@ -28,6 +28,12 @@
|
||||
*
|
||||
* The mask slot is written through &env[11]; on success the flag is set and
|
||||
* 0 is returned in eax, exactly like plain setjmp.
|
||||
*
|
||||
* rbx carries the env base across the syscall (rdi/rsi/rdx/r10 hold the
|
||||
* syscall arguments, rax the number, rcx/r11 are clobbered by the kernel).
|
||||
* rbx is callee-saved: its original value was stored in env[0] above, so it
|
||||
* is reloaded from there BEFORE the ret, leaving every callee-saved register
|
||||
* intact on the ordinary return path as the SysV AMD64 ABI requires.
|
||||
*/
|
||||
|
||||
.global __sigsetjmp
|
||||
@@ -51,7 +57,7 @@ sigsetjmp:
|
||||
fnstcw 72(%rdi)
|
||||
test %esi,%esi
|
||||
jz 1f
|
||||
mov %rdi,%rbx /* env base (rbx is restored from the buffer later) */
|
||||
mov %rdi,%rbx /* env base (scratch; caller rbx is in env[0]) */
|
||||
mov $14,%eax /* SYS_rt_sigprocmask */
|
||||
xor %edi,%edi /* how = SIG_BLOCK(0) */
|
||||
xor %esi,%esi /* set = NULL (query only) */
|
||||
@@ -59,6 +65,7 @@ sigsetjmp:
|
||||
mov $8,%r10d /* sigsetsize (x86_64 sigset_t = one word) */
|
||||
syscall
|
||||
movq $1,80(%rbx) /* mask saved: set the flag */
|
||||
mov 0(%rbx),%rbx /* restore the caller's rbx before returning */
|
||||
1:
|
||||
xor %eax,%eax
|
||||
ret
|
||||
|
||||
Reference in New Issue
Block a user