From 7daa086114c00cd8141c5d74f078f8124ab11a47 Mon Sep 17 00:00:00 2001 From: Philippe Waroquiers Date: Sat, 28 Jul 2018 00:36:35 +0200 Subject: [PATCH] Give some more information in the scheduler information thread status * In case a thread is executing a syscall, give the syscall no being executed. * Show the address range of the valgrind stack, similarly to the client stack --- coregrind/m_libcassert.c | 20 +++++++++++++++----- coregrind/m_syswrap/syswrap-main.c | 10 ++++++++-- coregrind/pub_core_syswrap.h | 7 +++++-- 3 files changed, 28 insertions(+), 9 deletions(-) diff --git a/coregrind/m_libcassert.c b/coregrind/m_libcassert.c index a75a650140..5afe1ce275 100644 --- a/coregrind/m_libcassert.c +++ b/coregrind/m_libcassert.c @@ -42,6 +42,7 @@ #include "pub_core_stacks.h" #include "pub_core_stacktrace.h" #include "pub_core_syscall.h" +#include "pub_core_syswrap.h" #include "pub_core_tooliface.h" // For VG_(details).{name,bug_reports_to} #include "pub_core_options.h" // For VG_(clo_xml) @@ -298,17 +299,25 @@ void VG_(client_exit)( Int status ) static void print_thread_state (Bool stack_usage, const HChar* prefix, ThreadId i) { - VgStack *stack + VgStack *stack = (VgStack*)VG_(threads)[i].os_state.valgrind_stack_base; - - VG_(printf)("\n%sThread %d: status = %s (lwpid %d)\n", prefix, i, + HChar syscallno[50]; + // must be large enough for VG_SYSNUM_STRING result + 10. + + if (VG_(is_in_syscall) (i)) + VG_(sprintf)(syscallno, " syscall %s", + VG_SYSNUM_STRING(VG_(is_in_syscall_no)(i))); + else + syscallno[0] = 0; + VG_(printf)("\n%sThread %d: status = %s%s (lwpid %d)\n", prefix, i, VG_(name_of_ThreadStatus)(VG_(threads)[i].status), + syscallno, VG_(threads)[i].os_state.lwpid); if (VG_(threads)[i].status != VgTs_Empty) VG_(get_and_pp_StackTrace)( i, BACKTRACE_DEPTH ); if (stack_usage && VG_(threads)[i].client_stack_highest_byte != 0 ) { Addr start, end; - + start = end = 0; VG_(stack_limits)(VG_(get_SP)(i), &start, &end); if (start != end) @@ -322,8 +331,9 @@ static void print_thread_state (Bool stack_usage, } if (stack_usage && stack != 0) VG_(printf) - ("%svalgrind stack top usage: %lu of %lu\n", + ("%svalgrind stack range: [%p %p] top usage: %lu of %lu\n", prefix, + (void*)stack, (void*)((Addr)stack + VG_(clo_valgrind_stacksize) - 1), VG_(clo_valgrind_stacksize) - VG_(am_get_VgStack_unused_szB) (stack, VG_(clo_valgrind_stacksize)), diff --git a/coregrind/m_syswrap/syswrap-main.c b/coregrind/m_syswrap/syswrap-main.c index acee5b5e24..a2876c5fb1 100644 --- a/coregrind/m_syswrap/syswrap-main.c +++ b/coregrind/m_syswrap/syswrap-main.c @@ -1628,7 +1628,7 @@ SyscallInfo *syscallInfo; /* The scheduler needs to be able to zero out these records after a fork, hence this is exported from m_syswrap. */ -void VG_(clear_syscallInfo) ( Int tid ) +void VG_(clear_syscallInfo) ( ThreadId tid ) { vg_assert(syscallInfo); vg_assert(tid >= 0 && tid < VG_N_THREADS); @@ -1636,12 +1636,18 @@ void VG_(clear_syscallInfo) ( Int tid ) syscallInfo[tid].status.what = SsIdle; } -Bool VG_(is_in_syscall) ( Int tid ) +Bool VG_(is_in_syscall) ( ThreadId tid ) { vg_assert(tid >= 0 && tid < VG_N_THREADS); return (syscallInfo[tid].status.what != SsIdle); } +Word VG_(is_in_syscall_no) (ThreadId tid ) +{ + vg_assert(tid >= 0 && tid < VG_N_THREADS); + return syscallInfo[tid].orig_args.sysno; +} + static void ensure_initialised ( void ) { Int i; diff --git a/coregrind/pub_core_syswrap.h b/coregrind/pub_core_syswrap.h index e8ba00561c..4e73c073a4 100644 --- a/coregrind/pub_core_syswrap.h +++ b/coregrind/pub_core_syswrap.h @@ -49,10 +49,13 @@ extern void VG_(client_syscall) ( ThreadId tid, UInt trc ); extern void VG_(post_syscall) ( ThreadId tid ); /* Clear this module's private state for thread 'tid' */ -extern void VG_(clear_syscallInfo) ( Int tid ); +extern void VG_(clear_syscallInfo) ( ThreadId tid ); // Returns True if the given thread is currently in a system call -extern Bool VG_(is_in_syscall) ( Int tid ); +extern Bool VG_(is_in_syscall) ( ThreadId tid ); + +// If VG_(is_in_syscall) (tid), returns the sysno the given thread is in +extern Word VG_(is_in_syscall_no) (ThreadId tid ); // Fix up a thread's state when syscall is interrupted by a signal. extern void VG_(fixup_guest_state_after_syscall_interrupted)( -- 2.47.2