Introduce NSIG_BYTES

* nsig.h (NSIG_BYTES): New macro.
* desc.c: Use it in comments instead of NSIG.
* epoll.c: Likewise.
* poll.c: Likewise.
* signalfd.c: Likewise.
* signal.c: Likewise.
(sprintsigmask_n, print_sigset_addr_len_limit): Use it instead of NSIG.
* linux/alpha/arch_sigreturn.c (arch_sigreturn): Likewise.
* linux/arm/arch_sigreturn.c (arch_sigreturn): Likewise.
* linux/crisv10/arch_sigreturn.c (arch_sigreturn): Likewise.
* linux/ia64/arch_sigreturn.c (arch_sigreturn): Likewise.
* linux/m68k/arch_sigreturn.c (arch_sigreturn): Likewise.
* linux/microblaze/arch_sigreturn.c (arch_sigreturn): Likewise.
* linux/mips/arch_sigreturn.c (arch_sigreturn): Likewise.
* linux/powerpc/arch_sigreturn.c (arch_sigreturn): Likewise.
* linux/s390/arch_sigreturn.c (arch_sigreturn): Likewise.
* linux/sparc/arch_sigreturn.c (arch_sigreturn): Likewise.
* linux/tile/arch_sigreturn.c (arch_sigreturn): Likewise.
* linux/x86_64/arch_sigreturn.c (arch_sigreturn): Likewise.
* tests/pselect6.c (main): Likewise.
This commit is contained in:
Дмитрий Левин 2016-12-27 23:32:44 +00:00
parent 5a25466437
commit e9c702f9ad
19 changed files with 39 additions and 36 deletions

2
desc.c
View File

@ -256,7 +256,7 @@ SYS_FUNC(pselect6)
if (!umove_kulong_array_or_printaddr(tcp, tcp->u_arg[5], if (!umove_kulong_array_or_printaddr(tcp, tcp->u_arg[5],
data, ARRAY_SIZE(data))) { data, ARRAY_SIZE(data))) {
tprints("{"); tprints("{");
/* NB: kernel requires data[1] == NSIG / 8 */ /* NB: kernel requires data[1] == NSIG_BYTES */
print_sigset_addr_len(tcp, data[0], data[1]); print_sigset_addr_len(tcp, data[0], data[1]);
tprintf(", %" PRI_klu "}", data[1]); tprintf(", %" PRI_klu "}", data[1]);
} }

View File

@ -109,7 +109,7 @@ SYS_FUNC(epoll_pwait)
epoll_wait_common(tcp); epoll_wait_common(tcp);
if (exiting(tcp)) { if (exiting(tcp)) {
tprints(", "); tprints(", ");
/* NB: kernel requires arg[5] == NSIG / 8 */ /* NB: kernel requires arg[5] == NSIG_BYTES */
print_sigset_addr_len(tcp, tcp->u_arg[4], tcp->u_arg[5]); print_sigset_addr_len(tcp, tcp->u_arg[4], tcp->u_arg[5]);
tprintf(", %" PRI_klu, tcp->u_arg[5]); tprintf(", %" PRI_klu, tcp->u_arg[5]);
} }

View File

@ -8,6 +8,6 @@ arch_sigreturn(struct tcb *tcp)
addr += offsetof(struct sigcontext, sc_mask); addr += offsetof(struct sigcontext, sc_mask);
tprints("{mask="); tprints("{mask=");
print_sigset_addr_len(tcp, addr, NSIG / 8); print_sigset_addr_len(tcp, addr, NSIG_BYTES);
tprints("}"); tprints("}");
} }

View File

@ -14,6 +14,6 @@ arch_sigreturn(struct tcb *tcp)
(*arm_sp_ptr + (*arm_sp_ptr +
OFFSETOF_STRUCT_UCONTEXT_UC_SIGMASK); OFFSETOF_STRUCT_UCONTEXT_UC_SIGMASK);
tprints("{mask="); tprints("{mask=");
print_sigset_addr_len(tcp, addr, NSIG / 8); print_sigset_addr_len(tcp, addr, NSIG_BYTES);
tprints("}"); tprints("}");
} }

View File

@ -11,6 +11,6 @@ arch_sigreturn(struct tcb *tcp)
regs[PT_USP] + offsetof(struct sigcontext, oldmask); regs[PT_USP] + offsetof(struct sigcontext, oldmask);
tprints("{mask="); tprints("{mask=");
print_sigset_addr_len(tcp, addr, NSIG / 8); print_sigset_addr_len(tcp, addr, NSIG_BYTES);
tprints("}"); tprints("}");
} }

View File

@ -7,6 +7,6 @@ arch_sigreturn(struct tcb *tcp)
OFFSETOF_STRUCT_SIGFRAME_SC + OFFSETOF_STRUCT_SIGFRAME_SC +
offsetof(struct sigcontext, sc_mask); offsetof(struct sigcontext, sc_mask);
tprints("{mask="); tprints("{mask=");
print_sigset_addr_len(tcp, addr, NSIG / 8); print_sigset_addr_len(tcp, addr, NSIG_BYTES);
tprints("}"); tprints("}");
} }

View File

@ -7,7 +7,7 @@ arch_sigreturn(struct tcb *tcp)
if (umove(tcp, *m68k_usp_ptr + 2 * sizeof(int), &addr) < 0) if (umove(tcp, *m68k_usp_ptr + 2 * sizeof(int), &addr) < 0)
return; return;
unsigned long mask[NSIG / 8 / sizeof(long)]; unsigned long mask[NSIG_BYTES / sizeof(long)];
/* Fetch first word of signal mask. */ /* Fetch first word of signal mask. */
if (umove(tcp, addr, &mask[0]) < 0) if (umove(tcp, addr, &mask[0]) < 0)
return; return;

View File

@ -11,6 +11,6 @@ arch_sigreturn(struct tcb *tcp)
addr += offsetof(struct sigcontext, oldmask); addr += offsetof(struct sigcontext, oldmask);
tprints("{mask="); tprints("{mask=");
print_sigset_addr_len(tcp, addr, NSIG / 8); print_sigset_addr_len(tcp, addr, NSIG_BYTES);
tprints("}"); tprints("}");
} }

View File

@ -21,6 +21,6 @@ arch_sigreturn(struct tcb *tcp)
#endif #endif
tprints("{mask="); tprints("{mask=");
print_sigset_addr_len(tcp, addr, NSIG / 8); print_sigset_addr_len(tcp, addr, NSIG_BYTES);
tprints("}"); tprints("}");
} }

View File

@ -15,7 +15,7 @@ arch_sigreturn(struct tcb *tcp)
if (umove(tcp, addr, &sc) < 0) { if (umove(tcp, addr, &sc) < 0) {
tprintf("{mask=%#lx}", addr); tprintf("{mask=%#lx}", addr);
} else { } else {
unsigned long mask[NSIG / 8 / sizeof(long)]; unsigned long mask[NSIG_BYTES / sizeof(long)];
#ifdef POWERPC64 #ifdef POWERPC64
mask[0] = sc.oldmask | (sc._unused[3] << 32); mask[0] = sc.oldmask | (sc._unused[3] << 32);
#else #else

View File

@ -1,7 +1,7 @@
static void static void
arch_sigreturn(struct tcb *tcp) arch_sigreturn(struct tcb *tcp)
{ {
unsigned long mask[NSIG / 8 / sizeof(long)]; unsigned long mask[NSIG_BYTES / sizeof(long)];
const unsigned long addr = *s390_frame_ptr + __SIGNAL_FRAMESIZE; const unsigned long addr = *s390_frame_ptr + __SIGNAL_FRAMESIZE;
if (umove(tcp, addr, &mask) < 0) { if (umove(tcp, addr, &mask) < 0) {

View File

@ -17,13 +17,13 @@ arch_sigreturn(struct tcb *tcp)
unsigned int mask; unsigned int mask;
char fpu_save[PERSONALITY_WORDSIZE]; char fpu_save[PERSONALITY_WORDSIZE];
char insns[PERSONALITY_WORDSIZE * 2] ATTRIBUTE_ALIGNED(8); char insns[PERSONALITY_WORDSIZE * 2] ATTRIBUTE_ALIGNED(8);
unsigned int extramask[NSIG / 8 / sizeof(int) - 1]; unsigned int extramask[NSIG_BYTES / sizeof(int) - 1];
} frame; } frame;
if (umove(tcp, addr, &frame) < 0) { if (umove(tcp, addr, &frame) < 0) {
tprintf("{mask=%#lx}", addr); tprintf("{mask=%#lx}", addr);
} else { } else {
unsigned int mask[NSIG / 8 / sizeof(int)]; unsigned int mask[NSIG_BYTES / sizeof(int)];
mask[0] = frame.mask; mask[0] = frame.mask;
memcpy(mask + 1, frame.extramask, sizeof(frame.extramask)); memcpy(mask + 1, frame.extramask, sizeof(frame.extramask));

View File

@ -7,6 +7,6 @@ arch_sigreturn(struct tcb *tcp)
offsetof(struct ucontext, uc_sigmask); offsetof(struct ucontext, uc_sigmask);
tprints("{mask="); tprints("{mask=");
print_sigset_addr_len(tcp, addr, NSIG / 8); print_sigset_addr_len(tcp, addr, NSIG_BYTES);
tprints("}"); tprints("}");
} }

View File

@ -27,6 +27,6 @@ arch_sigreturn(struct tcb *tcp)
#endif #endif
const kernel_ulong_t addr = (kernel_ulong_t) *x86_64_rsp_ptr + offset; const kernel_ulong_t addr = (kernel_ulong_t) *x86_64_rsp_ptr + offset;
tprints("{mask="); tprints("{mask=");
print_sigset_addr_len(tcp, addr, NSIG / 8); print_sigset_addr_len(tcp, addr, NSIG_BYTES);
tprints("}"); tprints("}");
} }

2
nsig.h
View File

@ -10,4 +10,6 @@
# error NSIG < 32 # error NSIG < 32
#endif #endif
#define NSIG_BYTES (NSIG / 8)
#endif /* !STRACE_NSIG_H */ #endif /* !STRACE_NSIG_H */

2
poll.c
View File

@ -176,7 +176,7 @@ SYS_FUNC(ppoll)
print_timespec(tcp, tcp->u_arg[2]); print_timespec(tcp, tcp->u_arg[2]);
tprints(", "); tprints(", ");
/* NB: kernel requires arg[4] == NSIG / 8 */ /* NB: kernel requires arg[4] == NSIG_BYTES */
print_sigset_addr_len(tcp, tcp->u_arg[3], tcp->u_arg[4]); print_sigset_addr_len(tcp, tcp->u_arg[3], tcp->u_arg[4]);
tprintf(", %" PRI_klu, tcp->u_arg[4]); tprintf(", %" PRI_klu, tcp->u_arg[4]);

View File

@ -104,7 +104,7 @@
* umoven(tcp, addr, sizeof(sigset_t), &sigset) * umoven(tcp, addr, sizeof(sigset_t), &sigset)
* may be a bad idea: it'll try to read much more data than needed * may be a bad idea: it'll try to read much more data than needed
* to fetch a sigset_t. * to fetch a sigset_t.
* Use (NSIG / 8) as a size instead. * Use NSIG_BYTES as a size instead.
*/ */
static const char * static const char *
@ -168,16 +168,17 @@ const char *
sprintsigmask_n(const char *prefix, const void *sig_mask, unsigned int bytes) sprintsigmask_n(const char *prefix, const void *sig_mask, unsigned int bytes)
{ {
/* /*
* The maximum number of signal names to be printed is NSIG * 2 / 3. * The maximum number of signal names to be printed
* is NSIG_BYTES * 8 * 2 / 3.
* Most of signal names have length 7, * Most of signal names have length 7,
* average length of signal names is less than 7. * average length of signal names is less than 7.
* The length of prefix string does not exceed 16. * The length of prefix string does not exceed 16.
*/ */
static char outstr[128 + 8 * (NSIG * 2 / 3)]; static char outstr[128 + 8 * (NSIG_BYTES * 8 * 2 / 3)];
char *s; char *s;
const uint32_t *mask; const uint32_t *mask;
uint32_t inverted_mask[NSIG / 32]; uint32_t inverted_mask[NSIG_BYTES / 4];
unsigned int size; unsigned int size;
int i; int i;
char sep; char sep;
@ -186,10 +187,10 @@ sprintsigmask_n(const char *prefix, const void *sig_mask, unsigned int bytes)
mask = sig_mask; mask = sig_mask;
/* length of signal mask in 4-byte words */ /* length of signal mask in 4-byte words */
size = (bytes >= NSIG / 8) ? NSIG / 32 : (bytes + 3) / 4; size = (bytes >= NSIG_BYTES) ? NSIG_BYTES / 4 : (bytes + 3) / 4;
/* check whether 2/3 or more bits are set */ /* check whether 2/3 or more bits are set */
if (popcount32(mask, size) >= size * 32 * 2 / 3) { if (popcount32(mask, size) >= size * (4 * 8) * 2 / 3) {
/* show those signals that are NOT in the mask */ /* show those signals that are NOT in the mask */
unsigned int j; unsigned int j;
for (j = 0; j < size; ++j) for (j = 0; j < size; ++j)
@ -199,7 +200,7 @@ sprintsigmask_n(const char *prefix, const void *sig_mask, unsigned int bytes)
} }
sep = '['; sep = '[';
for (i = 0; (i = next_set_bit(mask, i, size * 32)) >= 0; ) { for (i = 0; (i = next_set_bit(mask, i, size * (4 * 8))) >= 0; ) {
++i; ++i;
*s++ = sep; *s++ = sep;
if ((unsigned) i < nsignals) { if ((unsigned) i < nsignals) {
@ -239,14 +240,14 @@ print_sigset_addr_len_limit(struct tcb *const tcp, const kernel_ulong_t addr,
const kernel_ulong_t len, const unsigned int min_len) const kernel_ulong_t len, const unsigned int min_len)
{ {
/* /*
* Here len is usually equal to NSIG / 8 or current_wordsize. * Here len is usually equal to NSIG_BYTES or current_wordsize.
* But we code this defensively: * But we code this defensively:
*/ */
if (len < min_len || len > NSIG / 8) { if (len < min_len || len > NSIG_BYTES) {
printaddr(addr); printaddr(addr);
return; return;
} }
int mask[NSIG / 8 / sizeof(int)] = {}; int mask[NSIG_BYTES / sizeof(int)] = {};
if (umoven_or_printaddr(tcp, addr, len, mask)) if (umoven_or_printaddr(tcp, addr, len, mask))
return; return;
tprints(sprintsigmask_n("", mask, len)); tprints(sprintsigmask_n("", mask, len));
@ -447,7 +448,7 @@ SYS_FUNC(sigpending)
SYS_FUNC(rt_sigprocmask) SYS_FUNC(rt_sigprocmask)
{ {
/* Note: arg[3] is the length of the sigset. Kernel requires NSIG / 8 */ /* Note: arg[3] is the length of the sigset. Kernel requires NSIG_BYTES */
if (entering(tcp)) { if (entering(tcp)) {
printxval(sigprocmaskcmds, tcp->u_arg[0], "SIG_???"); printxval(sigprocmaskcmds, tcp->u_arg[0], "SIG_???");
tprints(", "); tprints(", ");
@ -529,7 +530,7 @@ decode_new_sigaction(struct tcb *const tcp, const kernel_ulong_t addr)
* or in tcp->u_arg[3] (all other), * or in tcp->u_arg[3] (all other),
* but kernel won't handle sys_rt_sigaction * but kernel won't handle sys_rt_sigaction
* with wrong sigset size (just returns EINVAL instead). * with wrong sigset size (just returns EINVAL instead).
* We just fetch the right size, which is NSIG / 8. * We just fetch the right size, which is NSIG_BYTES.
*/ */
tprintsigmask_val("", sa.sa_mask); tprintsigmask_val("", sa.sa_mask);
tprints(", sa_flags="); tprints(", sa_flags=");
@ -569,7 +570,7 @@ SYS_FUNC(rt_sigpending)
if (exiting(tcp)) { if (exiting(tcp)) {
/* /*
* One of the few syscalls where sigset size (arg[1]) * One of the few syscalls where sigset size (arg[1])
* is allowed to be <= NSIG / 8, not strictly ==. * is allowed to be <= NSIG_BYTES, not strictly ==.
* This allows non-rt sigpending() syscall * This allows non-rt sigpending() syscall
* to reuse rt_sigpending() code in kernel. * to reuse rt_sigpending() code in kernel.
*/ */
@ -582,7 +583,7 @@ SYS_FUNC(rt_sigpending)
SYS_FUNC(rt_sigsuspend) SYS_FUNC(rt_sigsuspend)
{ {
/* NB: kernel requires arg[1] == NSIG / 8 */ /* NB: kernel requires arg[1] == NSIG_BYTES */
print_sigset_addr_len(tcp, tcp->u_arg[0], tcp->u_arg[1]); print_sigset_addr_len(tcp, tcp->u_arg[0], tcp->u_arg[1]);
tprintf(", %" PRI_klu, tcp->u_arg[1]); tprintf(", %" PRI_klu, tcp->u_arg[1]);
@ -616,7 +617,7 @@ SYS_FUNC(rt_tgsigqueueinfo)
SYS_FUNC(rt_sigtimedwait) SYS_FUNC(rt_sigtimedwait)
{ {
/* NB: kernel requires arg[3] == NSIG / 8 */ /* NB: kernel requires arg[3] == NSIG_BYTES */
if (entering(tcp)) { if (entering(tcp)) {
print_sigset_addr_len(tcp, tcp->u_arg[0], tcp->u_arg[3]); print_sigset_addr_len(tcp, tcp->u_arg[0], tcp->u_arg[3]);
tprints(", "); tprints(", ");

View File

@ -36,7 +36,7 @@
static int static int
do_signalfd(struct tcb *tcp, int flags_arg) do_signalfd(struct tcb *tcp, int flags_arg)
{ {
/* NB: kernel requires arg[2] == NSIG / 8 */ /* NB: kernel requires arg[2] == NSIG_BYTES */
printfd(tcp, tcp->u_arg[0]); printfd(tcp, tcp->u_arg[0]);
tprints(", "); tprints(", ");
print_sigset_addr_len(tcp, tcp->u_arg[1], tcp->u_arg[2]); print_sigset_addr_len(tcp, tcp->u_arg[1], tcp->u_arg[2]);

View File

@ -85,7 +85,7 @@ int main(int ac, char **av)
"= 1 (out [%d])\n", "= 1 (out [%d])\n",
fds[1] + 1, fds[0], fds[1], fds[1] + 1, fds[0], fds[1],
fds[0], fds[1], fds[0], fds[1],
NSIG / 8, fds[1]); NSIG_BYTES, fds[1]);
/* /*
* Another simple one, with a timeout. * Another simple one, with a timeout.
@ -111,7 +111,7 @@ int main(int ac, char **av)
FD_SET(fds[1],set[0]); FD_SET(fds[1],set[0]);
assert(pselect(-1, NULL, set[0], NULL, NULL, &mask) == -1); assert(pselect(-1, NULL, set[0], NULL, NULL, &mask) == -1);
printf("pselect6(-1, NULL, %p, NULL, NULL, {[HUP CHLD], %u}) " printf("pselect6(-1, NULL, %p, NULL, NULL, {[HUP CHLD], %u}) "
"= -1 EINVAL (%m)\n", set[0], NSIG / 8); "= -1 EINVAL (%m)\n", set[0], NSIG_BYTES);
/* /*
* Another variant, with nfds exceeding FD_SETSIZE limit. * Another variant, with nfds exceeding FD_SETSIZE limit.
@ -124,7 +124,7 @@ int main(int ac, char **av)
assert(pselect(FD_SETSIZE + 1, set[0], set[1], NULL, &tm.ts, &mask) == 0); assert(pselect(FD_SETSIZE + 1, set[0], set[1], NULL, &tm.ts, &mask) == 0);
printf("pselect6(%d, [%d], [], NULL, {tv_sec=0, tv_nsec=123}, " printf("pselect6(%d, [%d], [], NULL, {tv_sec=0, tv_nsec=123}, "
"{[HUP CHLD], %u}) = 0 (Timeout)\n", "{[HUP CHLD], %u}) = 0 (Timeout)\n",
FD_SETSIZE + 1, fds[0], NSIG / 8); FD_SETSIZE + 1, fds[0], NSIG_BYTES);
/* /*
* See how timeouts are decoded. * See how timeouts are decoded.
@ -137,7 +137,7 @@ int main(int ac, char **av)
printf("pselect6(0, NULL, NULL, NULL, {tv_sec=0, tv_nsec=222222222}, " printf("pselect6(0, NULL, NULL, NULL, {tv_sec=0, tv_nsec=222222222}, "
"{[HUP CHLD], %u}) = " "{[HUP CHLD], %u}) = "
"? ERESTARTNOHAND (To be restarted if no handler)\n", "? ERESTARTNOHAND (To be restarted if no handler)\n",
NSIG / 8); NSIG_BYTES);
puts("--- SIGALRM {si_signo=SIGALRM, si_code=SI_KERNEL} ---"); puts("--- SIGALRM {si_signo=SIGALRM, si_code=SI_KERNEL} ---");
puts("+++ exited with 0 +++"); puts("+++ exited with 0 +++");