Increase default thread stack size to 64k and institute crude
overflow checks in scheduler_sanity().
git-svn-id: svn://svn.valgrind.org/valgrind/trunk@183 a5019735-40e9-0310-863c-91ae7b9d1cf9
diff --git a/vg_scheduler.c b/vg_scheduler.c
index 61ae9ce..010c0b1 100644
--- a/vg_scheduler.c
+++ b/vg_scheduler.c
@@ -553,8 +553,6 @@
vg_threads[tid_main].associated_mx = NULL;
vg_threads[tid_main].associated_cv = NULL;
vg_threads[tid_main].retval = NULL; /* not important */
- vg_threads[tid_main].stack_highest_word
- = vg_threads[tid_main].m_esp /* -4 ??? */;
for (i = 0; i < VG_N_THREAD_KEYS; i++)
vg_threads[tid_main].specifics[i] = NULL;
@@ -562,6 +560,9 @@
vg_tid_currently_in_baseBlock = tid_main;
VG_(save_thread_state) ( tid_main );
+ vg_threads[tid_main].stack_highest_word
+ = vg_threads[tid_main].m_esp /* -4 ??? */;
+
/* So now ... */
vg_assert(vg_tid_currently_in_baseBlock == VG_INVALID_THREADID);
}
@@ -1488,9 +1489,8 @@
#include <pthread.h>
#include <errno.h>
-#if !defined(PTHREAD_STACK_MIN)
-# define PTHREAD_STACK_MIN (16384 - VG_AR_CLIENT_STACKBASE_REDZONE_SZB)
-#endif
+#define VG_PTHREAD_STACK_MIN \
+ (VG_PTHREAD_STACK_SIZE - VG_AR_CLIENT_STACKBASE_REDZONE_SZB)
/* /usr/include/bits/pthreadtypes.h:
typedef unsigned long int pthread_t;
@@ -1717,7 +1717,7 @@
/* Consider allocating the child a stack, if the one it already has
is inadequate. */
- new_stk_szb = PTHREAD_STACK_MIN;
+ new_stk_szb = VG_PTHREAD_STACK_MIN;
if (new_stk_szb > vg_threads[tid].stack_size) {
/* Again, for good measure :) We definitely don't want to be
@@ -2537,15 +2537,15 @@
mx = vg_threads[i].associated_mx;
cv = vg_threads[i].associated_cv;
if (vg_threads[i].status == VgTs_WaitMX) {
- /* If we're waiting on a MX: (1) the mx is not null, (2, 3)
- it's actually held by someone, since otherwise this thread
- is deadlocked, (4) the mutex's owner is not us, since
- otherwise this thread is also deadlocked. The logic in
- do_pthread_mutex_lock rejects attempts by a thread to lock
- a (non-recursive) mutex which it already owns.
+ /* If we're waiting on a MX: (1) the mx is not null, (2, 3)
+ it's actually held by someone, since otherwise this thread
+ is deadlocked, (4) the mutex's owner is not us, since
+ otherwise this thread is also deadlocked. The logic in
+ do_pthread_mutex_lock rejects attempts by a thread to lock
+ a (non-recursive) mutex which it already owns.
- (2) has been seen to fail sometimes. I don't know why.
- Possibly to do with signals. */
+ (2) has been seen to fail sometimes. I don't know why.
+ Possibly to do with signals. */
vg_assert(cv == NULL);
/* 1 */ vg_assert(mx != NULL);
/* 2 */ vg_assert(mx->__m_count > 0);
@@ -2561,6 +2561,26 @@
/* vg_assert(cv == NULL); */
/* vg_assert(mx == NULL); */
}
+
+ if (vg_threads[i].status != VgTs_Empty) {
+ Int
+ stack_used = (Addr)vg_threads[i].stack_highest_word
+ - (Addr)vg_threads[i].m_esp;
+ if (i > 1 /* not the root thread */
+ && stack_used
+ >= (VG_PTHREAD_STACK_MIN - 1000 /* paranoia */)) {
+ VG_(message)(Vg_UserMsg,
+ "Warning: STACK OVERFLOW: "
+ "thread %d: stack used %d, available %d",
+ i, stack_used, VG_PTHREAD_STACK_MIN );
+ VG_(message)(Vg_UserMsg,
+ "Terminating Valgrind. If thread(s) "
+ "really need more stack, increase");
+ VG_(message)(Vg_UserMsg,
+ "VG_PTHREAD_STACK_SIZE in vg_include.h and recompile.");
+ VG_(exit)(1);
+ }
+ }
}
for (i = 0; i < VG_N_THREAD_KEYS; i++) {