fix 3m bug relted to the deep end of a stack-segment copy

svn: r3592
This commit is contained in:
Matthew Flatt 2006-07-04 14:46:08 +00:00
parent ba5c6607d8
commit d44151a6f3
14 changed files with 356 additions and 323 deletions

69
src/configure vendored
View File

@ -5021,6 +5021,75 @@ _ACEOF
msg="for stack direction"
echo "$as_me:$LINENO: checking $msg" >&5
echo $ECHO_N "checking $msg... $ECHO_C" >&6
if test "$cross_compiling" = yes; then
stack_direction=unknown
else
cat >conftest.$ac_ext <<_ACEOF
/* confdefs.h. */
_ACEOF
cat confdefs.h >>conftest.$ac_ext
cat >>conftest.$ac_ext <<_ACEOF
/* end confdefs.h. */
int grows_down_p(int n, void *cmp) {
if (!cmp)
return grows_down_p(10, &cmp);
else if (!n)
return ((unsigned long)&cmp < (unsigned long)cmp);
else
return grows_down_p(n - 1, cmp);
}
int main() {
return grows_down_p();
}
_ACEOF
rm -f conftest$ac_exeext
if { (eval echo "$as_me:$LINENO: \"$ac_link\"") >&5
(eval $ac_link) 2>&5
ac_status=$?
echo "$as_me:$LINENO: \$? = $ac_status" >&5
(exit $ac_status); } && { ac_try='./conftest$ac_exeext'
{ (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5
(eval $ac_try) 2>&5
ac_status=$?
echo "$as_me:$LINENO: \$? = $ac_status" >&5
(exit $ac_status); }; }; then
stack_direction=up
else
echo "$as_me: program exited with status $ac_status" >&5
echo "$as_me: failed program was:" >&5
sed 's/^/| /' conftest.$ac_ext >&5
( exit $ac_status )
stack_direction=down
fi
rm -f core *.core gmon.out bb.out conftest$ac_exeext conftest.$ac_objext conftest.$ac_ext
fi
echo "$as_me:$LINENO: result: $stack_direction" >&5
echo "${ECHO_T}$stack_direction" >&6
if test "${stack_direction}" = "uknown" ; then
echo configure: cannot determine stack direction
exit 1
fi
if test "${stack_direction}" = "up" ; then
cat >>confdefs.h <<\_ACEOF
#define STACK_DIRECTION 1
_ACEOF
fi
if test "${stack_direction}" = "down" ; then
cat >>confdefs.h <<\_ACEOF
#define STACK_DIRECTION -1
_ACEOF
fi
###### Some flags imply other flags #######
if test "${enable_smalloskit}" = "yes" ; then

View File

@ -89,6 +89,34 @@ AC_CHECK_SIZEOF(int)
AC_CHECK_SIZEOF(long)
AC_CHECK_SIZEOF(long long)
[ msg="for stack direction" ]
AC_MSG_CHECKING($msg)
AC_TRY_RUN(
int grows_down_p(int n, void *cmp) {
if (!cmp)
return grows_down_p(10, &cmp);
else if (!n)
return ((unsigned long)&cmp < (unsigned long)cmp);
else
return grows_down_p(n - 1, cmp);
}
int main() {
return grows_down_p();
}, stack_direction=up, stack_direction=down, stack_direction=unknown)
AC_MSG_RESULT($stack_direction)
if test "${stack_direction}" = "uknown" ; then
echo configure: cannot determine stack direction
exit 1
fi
if test "${stack_direction}" = "up" ; then
AC_DEFINE(STACK_DIRECTION,1,[Stack direction up])
fi
if test "${stack_direction}" = "down" ; then
AC_DEFINE(STACK_DIRECTION,-1,[Stack direction down])
fi
###### Some flags imply other flags #######
if test "${enable_smalloskit}" = "yes" ; then

View File

@ -288,8 +288,9 @@ main.@LTO@: $(XSRCDIR)/main.c
$(CC) $(CFLAGS) -c $(XSRCDIR)/main.c -o main.@LTO@
gc2.@LTO@: $(srcdir)/gc2.c $(srcdir)/newgc.c $(srcdir)/compact.c $(srcdir)/newgc.c $(srcdir)/gc2.h \
$(srcdir)/vm_osx.c $(srcdir)/vm_mmap.c $(srcdir)/vm_osk.c $(srcdir)/alloc_cache.c $(srcdir)/my_qsort.c \
$(srcdir)/page_range.c $(srcdir)/protect_range.c $(srcdir)/../utils/splay.c \
$(srcdir)/vm_osx.c $(srcdir)/vm_mmap.c $(srcdir)/vm_osk.c $(srcdir)/alloc_cache.c \
$(srcdir)/page_range.c $(srcdir)/protect_range.c $(srcdir)/var_stack.c $(srcdir)/stack_comp.c \
$(srcdir)/../utils/splay.c $(srcdir)/my_qsort.c \
$(srcdir)/weak.c $(srcdir)/fnls.c $(srcdir)/../include/scheme.h $(srcdir)/../src/schpriv.h
$(CC) $(CFLAGS) -c $(srcdir)/gc2.c -o gc2.@LTO@

View File

@ -89,8 +89,8 @@ typedef short Type_Tag;
/* Debugging and performance tools: */
#define TIME 0
#define SEARCH 0
#define CHECKS 0
#define CHECK_STACK_PTRS 0
#define CHECKS 1
#define CHECK_STACK_PTRS 1
#define NOISY 0
#define MARK_STATS 0
#define ALLOC_GC_PHASE 0
@ -2720,124 +2720,27 @@ static int stack_depth;
static int record_stack_source = 0;
#endif
void GC_mark_variable_stack(void **var_stack,
long delta,
void *limit)
{
long size, count;
void ***p, **a;
#include "stack_comp.c"
#if TIME
stack_depth = 0;
#endif
while (var_stack) {
var_stack = (void **)((char *)var_stack + delta);
if (var_stack == limit)
return;
size = *(long *)(var_stack + 1);
#if CHECKS
oo_var_stack = o_var_stack;
o_var_stack = var_stack;
#endif
p = (void ***)(var_stack + 2);
while (size--) {
a = *p;
if (!a) {
/* Array */
count = ((long *)p)[2];
a = ((void ***)p)[1];
p += 2;
size -= 2;
a = (void **)((char *)a + delta);
while (count--) {
#define GC_X_variable_stack GC_mark_variable_stack
#if RECORD_MARK_SRC
if (record_stack_source) {
mark_src = a;
mark_type = MTYPE_STACK;
}
# define X_source(p) if (record_stack_source) { mark_src = p; mark_type = MTYPE_STACK; }
#else
# define X_source(p) /* */
#endif
gcMARK(*a);
a++;
}
} else {
a = (void **)((char *)a + delta);
#if RECORD_MARK_SRC
if (record_stack_source) {
mark_src = a;
mark_type = MTYPE_STACK;
}
#endif
gcMARK(*a);
}
p++;
}
#define gcX(p) gcMARK(p)
#include "var_stack.c"
#undef GC_X_variable_stack
#undef gcX
#undef X_source
#if 0
if (*var_stack && ((unsigned long)*var_stack < (unsigned long)var_stack)) {
GCPRINT(GCOUTF, "bad %d\n", stack_depth);
CRASH(32);
}
#endif
var_stack = *var_stack;
#if TIME
stack_depth++;
#endif
}
}
void GC_fixup_variable_stack(void **var_stack,
long delta,
void *limit)
{
long size, count;
void ***p, **a;
#if TIME
stack_depth = 0;
#endif
while (var_stack) {
var_stack = (void **)((char *)var_stack + delta);
if (var_stack == limit)
return;
size = *(long *)(var_stack + 1);
p = (void ***)(var_stack + 2);
while (size--) {
a = *p;
if (!a) {
/* Array */
count = ((long *)p)[2];
a = ((void ***)p)[1];
p += 2;
size -= 2;
a = (void **)((char *)a + delta);
while (count--) {
gcFIXUP(*a);
a++;
}
} else {
a = (void **)((char *)a + delta);
gcFIXUP(*a);
}
p++;
}
var_stack = *var_stack;
#if TIME
stack_depth++;
#endif
}
}
#define GC_X_variable_stack GC_fixup_variable_stack
#define gcX(p) gcFIXUP(p)
#define X_source(p) /* */
#include "var_stack.c"
#undef GC_X_variable_stack
#undef gcX
#undef X_source
#if CHECKS
# if CHECK_STACK_PTRS
@ -2899,6 +2802,11 @@ void GC_check_variable_stack()
if (*var_stack && ((unsigned long)*var_stack <= (unsigned long)var_stack))
CRASH(33);
# endif
size = *(long *)(var_stack + 1);
if (var_stack + size + 2 == limit)
return;
# if CHECK_STACK_PTRS
size = *(long *)(var_stack + 1);

View File

@ -486,6 +486,8 @@ void *GC_malloc_one_small_tagged(size_t sizeb)
{
unsigned long newsize;
return GC_malloc_one_tagged(sizeb);
sizeb += WORD_SIZE;
sizeb = ALIGN_BYTES_SIZE(sizeb);
newsize = gen0_alloc_page->size + sizeb;
@ -805,114 +807,27 @@ unsigned long GC_get_stack_base()
return stack_base;
}
#define traverse_stack(var_stack, delta, limit, operation) { \
long size, count; \
void ***p, **a; \
\
while(var_stack) { \
var_stack = (void **)((char *)var_stack + delta); \
if(var_stack == limit) return; \
\
size = *(long*)(var_stack + 1); p = (void***)(var_stack + 2); \
while(size--) { \
a = *p; \
if(!a) { \
count = ((long *)p)[2]; a = ((void***)p)[1]; \
p += 2; size -= 2; a = (void**)((char *)a + delta); \
while(count--) { operation(*a); a++; } \
} else { \
a = (void**)((char *)a + delta); operation(*a); \
} \
p++; \
} \
var_stack = *var_stack; \
} \
}
#define gc_stack_base ((void*)(GC_get_thread_stack_base \
? GC_get_thread_stack_base() \
: (unsigned long)stack_base))
/* these names are fixed by the gc2 spec; which is a bit unfortunate */
void GC_mark_variable_stack(void **var_stack, long delta, void *limit)
{
long size, count;
void ***p, **a;
#include "stack_comp.c"
while (var_stack) {
var_stack = (void **)((char *)var_stack + delta);
if (var_stack == limit)
return;
#define GC_X_variable_stack GC_mark_variable_stack
#define gcX(p) gcMARK(p)
#define X_source(p) set_backtrace_source(p, BT_STACK)
#include "var_stack.c"
#undef GC_X_variable_stack
#undef gcX
#undef X_source
size = *(long *)(var_stack + 1);
p = (void ***)(var_stack + 2);
while (size--) {
a = *p;
if (!a) {
/* Array */
count = ((long *)p)[2];
a = ((void ***)p)[1];
p += 2;
size -= 2;
a = (void **)((char *)a + delta);
while (count--) {
set_backtrace_source(a, BT_STACK);
gcMARK(*a);
a++;
}
} else {
a = (void **)((char *)a + delta);
set_backtrace_source(a, BT_STACK);
gcMARK(*a);
}
p++;
}
var_stack = *var_stack;
}
/* traverse_stack(var_stack, delta, limit, gcMARK); */
}
void GC_fixup_variable_stack(void **var_stack, long delta, void *limit)
{
long size, count;
void ***p, **a;
while (var_stack) {
var_stack = (void **)((char *)var_stack + delta);
if (var_stack == limit)
return;
size = *(long *)(var_stack + 1);
p = (void ***)(var_stack + 2);
while (size--) {
a = *p;
if (!a) {
/* Array */
count = ((long *)p)[2];
a = ((void ***)p)[1];
p += 2;
size -= 2;
a = (void **)((char *)a + delta);
while (count--) {
gcFIXUP(*a);
a++;
}
} else {
a = (void **)((char *)a + delta);
gcFIXUP(*a);
}
p++;
}
var_stack = *var_stack;
}
/* traverse_stack(var_stack, delta, limit, gcFIXUP); */
}
#define GC_X_variable_stack GC_fixup_variable_stack
#define gcX(p) gcFIXUP(p)
#define X_source(p) /* */
#include "var_stack.c"
#undef GC_X_variable_stack
#undef gcX
#undef X_source
/*****************************************************************************/
/* Routines for root sets */
@ -1795,7 +1710,7 @@ int GC_set_account_hook(int type, void *c1, unsigned long b, void *c2)
/* administration / initialization */
/*****************************************************************************/
static int generations_available = 1;
static int generations_available = 0;
void designate_modified(void *p)
{

View File

@ -0,0 +1,7 @@
#include "mzconfig.h"
#if STACK_DIRECTION > 0
# define SHALLOWER_STACK_ADDRESS(a, b) ((unsigned long)a > (unsigned long)b)
#else
# define SHALLOWER_STACK_ADDRESS(a, b) ((unsigned long)a < (unsigned long)b)
#endif

View File

@ -0,0 +1,84 @@
void GC_X_variable_stack(void **var_stack, long delta, void *limit)
{
long size, count;
void ***p, **a;
#if TIME
stack_depth = 0;
#endif
while (var_stack) {
var_stack = (void **)((char *)var_stack + delta);
size = *(long *)(var_stack + 1);
p = (void ***)(var_stack + 2);
#if CHECKS
oo_var_stack = o_var_stack;
o_var_stack = var_stack;
#endif
if ((var_stack == limit)
|| (var_stack + size + 2 == limit)) {
/* Last frame: need to X things that are shallower than the
limit: */
while (size--) {
a = *p;
if (!a) {
/* Array */
count = ((long *)p)[2];
a = ((void ***)p)[1];
p += 2;
size -= 2;
a = (void **)((char *)a + delta);
if (SHALLOWER_STACK_ADDRESS(a, limit)) {
while (count--) {
X_source(a);
gcX(*a);
a++;
}
}
} else {
a = (void **)((char *)a + delta);
if (SHALLOWER_STACK_ADDRESS(a, limit)) {
X_source(a);
gcX(*a);
}
}
p++;
}
return;
}
while (size--) {
a = *p;
if (!a) {
/* Array */
count = ((long *)p)[2];
a = ((void ***)p)[1];
p += 2;
size -= 2;
a = (void **)((char *)a + delta);
while (count--) {
X_source(a);
gcX(*a);
a++;
}
} else {
a = (void **)((char *)a + delta);
X_source(a);
gcX(*a);
}
p++;
}
var_stack = *var_stack;
#if TIME
stack_depth++;
#endif
}
}

View File

@ -1,6 +1,9 @@
/* This file contains information that was gathered by the configure script. */
#ifndef __MZSCHEME_CONFIGURATION_INFO__
#define __MZSCHEME_CONFIGURATION_INFO__
/* The size of a `char', as computed by sizeof. */
#undef SIZEOF_CHAR
@ -17,9 +20,14 @@
/* The size of a `long long', as computed by sizeof. */
#undef SIZEOF_LONG_LONG
/* Direction of stack growth: 1 = up, -1 = down, 0 = unknown */
#undef STACK_DIRECTION
/* whether nl_langinfo works */
#undef HAVE_CODESET
/* whether getaddrinfo works */
#undef HAVE_GETADDRINFO
#endif

View File

@ -27,7 +27,6 @@
# define SYSTEM_TYPE_NAME "oskit"
# define STACK_GROWS_DOWN
# define DO_STACK_CHECK
# ifndef OSKIT_TEST
# define OSKIT_FIXED_STACK_BOUNDS
@ -83,7 +82,6 @@
# include "uconfig.h"
# define STACK_GROWS_DOWN
# ifndef i386
# define SCHEME_BIG_ENDIAN
# endif
@ -138,7 +136,6 @@
# include "uconfig.h"
# undef USE_FCHDIR
# define STACK_GROWS_DOWN
# define SCHEME_BIG_ENDIAN
# define UNIX_LIMIT_STACK 33554944
@ -209,10 +206,7 @@
# endif
# if defined(__hppa__)
# define STACK_GROWS_UP
# define SIXTY_FOUR_BIT_INTEGERS
# else
# define STACK_GROWS_DOWN
# endif
# define USE_IEEE_FP_PREDS
@ -254,8 +248,6 @@
# undef HAS_STANDARD_IOB
# define HAS_BSD_IOB
# define STACK_GROWS_DOWN
#ifndef __ELF__
# define UNDERSCORE_DYNLOAD_SYMBOL_PREFIX
#endif
@ -296,8 +288,6 @@
# define HAS_BSD_IOB
# define STACK_GROWS_DOWN
#ifndef __ELF__
# define UNDERSCORE_DYNLOAD_SYMBOL_PREFIX
#endif
@ -331,8 +321,6 @@
# define HAS_BSD_IOB
# define STACK_GROWS_DOWN
# ifdef FREEBSD_VERSION_2x
# define UNDERSCORE_DYNLOAD_SYMBOL_PREFIX
# endif
@ -367,7 +355,6 @@
# include "uconfig.h"
# define STACK_GROWS_DOWN
# define SCHEME_BIG_ENDIAN
# define DIRENT_NO_NAMLEN
@ -402,7 +389,6 @@
# define DIRENT_NO_NAMLEN
# define STACK_GROWS_DOWN
# define SCHEME_BIG_ENDIAN
# define NO_USLEEP
@ -420,8 +406,6 @@
# include "uconfig.h"
# define STACK_GROWS_DOWN
# define SIXTY_FOUR_BIT_INTEGERS
# define ALPHA_CONTROL_FP
@ -441,7 +425,6 @@
# include "uconfig.h"
# define STACK_GROWS_UP
# define SCHEME_BIG_ENDIAN
# define SOME_FDS_ARE_NOT_SELECTABLE
@ -480,8 +463,6 @@
# define HAS_SCO_IOB
# define STACK_GROWS_DOWN
# define USE_SCO_IEEE_FP_PREDS
# define USE_EXPLICT_FP_FORM_CHECK
# define USE_FCNTL_O_NONBLOCK
@ -522,7 +503,6 @@
# define GETENV_FUNCTION
# define DIR_FUNCTION
# define STACK_GROWS_DOWN
# define DO_STACK_CHECK
# define WINDOWS_FIND_STACK_BOUNDS
@ -628,7 +608,6 @@
# define USE_DIVIDE_MAKE_INFINITY
# define STACK_GROWS_DOWN
# define DO_STACK_CHECK
# define WINDOWS_FIND_STACK_BOUNDS
@ -670,7 +649,6 @@
# define SYSTEM_TYPE_NAME "macosx"
#endif
# define STACK_GROWS_DOWN
#ifdef __POWERPC__
# define SCHEME_BIG_ENDIAN
#endif
@ -713,7 +691,6 @@
# include "uconfig.h"
# define STACK_GROWS_DOWN
# define USE_MAP_ANON
# define USE_DYNAMIC_FDSET_SIZE
@ -769,7 +746,6 @@
# define LINK_EXTENSIONS_BY_TABLE
# endif
# define STACK_GROWS_DOWN
# define SCHEME_BIG_ENDIAN
# define DO_STACK_CHECK
@ -827,8 +803,6 @@
# define GETENV_FUNCTION
# define DIR_FUNCTION
# define STACK_GROWS_DOWN
# define DO_STACK_CHECK
# define USE_STACKAVAIL
# define STACK_SAFETY_MARGIN 15000
@ -863,7 +837,6 @@
# define NO_USER_BREAK_HANDLER
# define NO_USLEEP
# define STACK_GROWS_DOWN
# define SCHEME_BIG_ENDIAN
# define DO_STACK_CHECK
@ -1249,14 +1222,6 @@
# define UNIX_FIND_STACK_BOUNDS
# define STACK_SAFETY_MARGIN 50000
/* STACK_GROWS_UP means that deeper stack values have higher
numbered addresses.
STACK_GROWS_DOWN means that deeper stack values have lower
numbered addresses. This is usually the case (Sparc and
Intel platforms, for example, use this).
Use only one or none of these. (It's faster if you know which
one applies, but it can also be figured it out dynamically.) */
/* DO_STACK_CHECK checks for stack overflow during execution.
Requires either UNIX_FIND_STACK_BOUNDS, USE_STACKAVAIL,
MACOS_FIND_STACK_BOUNDS, or ASSUME_FIXED_STACK_SIZE. */

View File

@ -135,8 +135,6 @@ Scheme_Object *scheme_multiple_values;
volatile int scheme_fuel_counter;
int scheme_stack_grows_up;
int scheme_startup_use_jit = 1;
void scheme_set_startup_use_jit(int v) { scheme_startup_use_jit = v; }
@ -540,17 +538,17 @@ scheme_handle_stack_overflow(Scheme_Object *(*k)(void))
void scheme_init_stack_check()
/* Finds the C stack limit --- platform-specific. */
{
int *v;
int *v, stack_grows_up;
unsigned long deeper;
#ifdef UNIX_FIND_STACK_BOUNDS
struct rlimit rl;
#endif
deeper = scheme_get_deeper_address();
scheme_stack_grows_up = (deeper > (unsigned long)&v);
stack_grows_up = (deeper > (unsigned long)&v);
#ifdef STACK_GROWS_UP
if (!scheme_stack_grows_up) {
if (!stack_grows_up) {
if (scheme_console_printf)
scheme_console_printf("Stack grows DOWN, not UP.\n");
else
@ -559,7 +557,7 @@ void scheme_init_stack_check()
}
#endif
#ifdef STACK_GROWS_DOWN
if (scheme_stack_grows_up) {
if (stack_grows_up) {
if (scheme_console_printf)
scheme_console_printf("Stack grows UP, not DOWN.\n");
else
@ -570,7 +568,7 @@ void scheme_init_stack_check()
#ifdef ASSUME_FIXED_STACK_SIZE
scheme_stack_boundary = scheme_get_stack_base();
if (scheme_stack_grows_up)
if (stack_grows_up)
scheme_stack_boundary += (FIXED_STACK_SIZE - STACK_SAFETY_MARGIN);
else
scheme_stack_boundary += (STACK_SAFETY_MARGIN - FIXED_STACK_SIZE);
@ -618,7 +616,7 @@ void scheme_init_stack_check()
lim = UNIX_STACK_MAXIMUM;
# endif
if (scheme_stack_grows_up)
if (stack_grows_up)
bnd += (lim - STACK_SAFETY_MARGIN);
else
bnd += (STACK_SAFETY_MARGIN - lim);

View File

@ -2714,14 +2714,12 @@ static Scheme_Object *udp_bind_or_connect(const char *name, int argc, Scheme_Obj
}
errid = SOCK_ERRNO();
} else {
int ok;
int ok = 1;
#ifdef USE_NULL_TO_DISCONNECT_UDP
if (!origid) {
if (udp->connected)
ok = !connect(udp->s, NULL, 0);
else
ok = 1;
} else
#endif
{

View File

@ -25,21 +25,24 @@
/* If stacks grow up then */
#if !defined(STACK_GROWS_UP) && !defined(STACK_GROWS_DOWN)
# define STACK_GROWS_UNKNOWN
/* STACK_GROWS_UP means that deeper stack values have higher
numbered addresses.
STACK_GROWS_DOWN means that deeper stack values have lower
numbered addresses. This is usually the case (Sparc and
Intel platforms, for example, use this). */
#if STACK_DIRECTION > 0
# define STACK_GROWS_UP
#else
# define STACK_GROWS_DOWN
#endif
#ifdef STACK_GROWS_UP
# define STK_COMP(a,b) ((a) > (b))
# define STK_DIFF(a, b) ((a) - (b))
#else
# ifdef STACK_GROWS_DOWN
# define STK_COMP(a,b) ((a) < (b))
# define STK_COMP(a,b) ((a) < (b))
# define STK_DIFF(a, b) ((b) - (a))
# else
# define STK_COMP(a,b) (scheme_stack_grows_up == ((a) > (b)))
# define STK_DIFF(a,b) (scheme_stack_grows_up ? ((b) - (a)) : ((a) - (b)))
# endif
#endif
#ifdef SHORT_ALIGN
@ -48,8 +51,6 @@ typedef short stack_val;
typedef long stack_val;
#endif
extern int scheme_stack_grows_up;
#ifndef STACK_SAFETY_MARGIN
# define STACK_SAFETY_MARGIN 50000
#endif

View File

@ -28,14 +28,9 @@
#include "schgc.h"
#ifdef STACK_GROWS_UP
#define DEEPPOS(b) ((unsigned long)(b)->stack_from+(unsigned long)(b)->stack_size)
# define DEEPPOS(b) ((unsigned long)(b)->stack_from+(unsigned long)(b)->stack_size)
#else
#ifdef STACK_GROWS_DOWN
#define DEEPPOS(b) ((unsigned long)(b)->stack_from)
#else
#define DEEPPOS(b) ((unsigned long)(b)->stack_from+ \
(scheme_stack_grows_up ? (unsigned long)(b)->stack_size : 0))
#endif
# define DEEPPOS(b) ((unsigned long)(b)->stack_from)
#endif
#ifdef MZ_PRECISE_GC
@ -258,12 +253,12 @@ void scheme_copy_stack(Scheme_Jumpup_Buf *b, void *base, void *start GC_VAR_STAC
here = &size;
size = (long)here XFORM_OK_MINUS (long)start;
if (scheme_stack_grows_up) {
b->stack_from = start;
} else {
size = -size;
b->stack_from = here;
}
#ifdef STACK_GROWS_UP
b->stack_from = start;
#else
size = -size;
b->stack_from = here;
#endif
if (size < 0)
size = 0;
@ -361,16 +356,16 @@ static void uncopy_stack(int ok, Scheme_Jumpup_Buf *b, long *prev)
memcpy(cto, cfrom, size);
if (c->cont) {
if (scheme_stack_grows_up) {
top_delta = ((unsigned long)c->stack_from
- ((unsigned long)c->cont->buf.stack_from
+ c->cont->buf.stack_size));
} else {
bottom_delta = ((unsigned long)c->stack_from
+ c->stack_size
- (unsigned long)c->cont->buf.stack_from);
top_delta = bottom_delta;
}
#ifdef STACK_GROWS_UP
top_delta = ((unsigned long)c->stack_from
- ((unsigned long)c->cont->buf.stack_from
+ c->cont->buf.stack_size));
#else
bottom_delta = ((unsigned long)c->stack_from
+ c->stack_size
- (unsigned long)c->cont->buf.stack_from);
top_delta = bottom_delta;
#endif
c = &c->cont->buf;
} else
c = NULL;
@ -411,19 +406,19 @@ static long find_same(char *p, char *low, long max_size)
max_size = MAX_STACK_DIFF;
}
if (scheme_stack_grows_up) {
while (max_size--) {
if (p[cnt] != low[cnt])
break;
cnt++;
}
} else {
while (max_size--) {
if (p[max_size] != low[max_size])
break;
cnt++;
}
#ifdef STACK_GROWS_UP
while (max_size--) {
if (p[cnt] != low[cnt])
break;
cnt++;
}
#else
while (max_size--) {
if (p[max_size] != low[max_size])
break;
cnt++;
}
#endif
if (cnt & (SHARED_STACK_ALIGNMENT - 1)) {
cnt -= (cnt & (SHARED_STACK_ALIGNMENT - 1));
@ -435,15 +430,63 @@ static long find_same(char *p, char *low, long max_size)
#ifdef MZ_PRECISE_GC
static void *align_var_stack(void **vs, void *s)
{
void **nvs, **next;
long i, cnt;
void *a;
while (STK_COMP((unsigned long)vs, (unsigned long)s)) {
vs = (void **)(*vs);
}
return (void *)vs;
s = (void *)vs;
/* Check next few frames to see whether they refer to variables
before s. This can happen due to inlining, so that an older
frame is shallower in the stack. It shouldn't happen much,
though. */
nvs = *vs;
while (nvs) {
next = NULL;
cnt = ((long *)nvs)[1];
for (i = 0; i < cnt; i++) {
a = nvs[i+2];
if (!a) {
a = nvs[i+3];
i += 2;
}
if (STK_COMP((unsigned long)a, (unsigned long)s)) {
/* We need nvs to update part of copied stack! */
vs = nvs;
s = (void *)vs;
next = *nvs;
break;
}
}
nvs = next;
}
return s;
}
#define ALIGN_VAR_STACK(vs, s) s = align_var_stack(vs, s)
static void *shift_var_stack(void *s)
{
#ifdef STACK_GROWS_UP
return s;
#else
void **vs = (void **)s;
long cnt;
/* Set s past end of vs: */
cnt = ((long *)vs)[1];
return (void *)(vs + cnt + 2);
#endif
}
#define PAST_VAR_STACK(s) s = shift_var_stack(s);
END_XFORM_SKIP;
#else
# define ALIGN_VAR_STACK(vs, s) /* empty */
# define PAST_VAR_STACK(s) /* empty */
#endif
int scheme_setjmpup_relative(Scheme_Jumpup_Buf *b, void *base,
@ -458,9 +501,6 @@ int scheme_setjmpup_relative(Scheme_Jumpup_Buf *b, void *base,
FLUSH_REGISTER_WINDOWS;
if (STK_COMP((unsigned long)start, (unsigned long)&local))
start = (void *)&local;
if (!(local = scheme_setjmp(b->buf))) {
if (c) {
/* We'd like to re-use the stack copied for a continuation
@ -481,17 +521,19 @@ int scheme_setjmpup_relative(Scheme_Jumpup_Buf *b, void *base,
START_XFORM_SKIP;
same_size = find_same(get_copy(c->buf.stack_copy), c->buf.stack_from, c->buf.stack_size);
b->cont = c;
if (scheme_stack_grows_up) {
start = (void *)((char *)c->buf.stack_from + same_size);
} else {
start = (void *)((char *)c->buf.stack_from + (c->buf.stack_size - same_size));
}
/* In 3m-mode, we need to copy on a var-stack boundary: */
#ifdef STACK_GROWS_UP
start = (void *)((char *)c->buf.stack_from + same_size);
#else
start = (void *)((char *)c->buf.stack_from + (c->buf.stack_size - same_size));
#endif
/* In 3m-mode, we need `start' on a var-stack boundary: */
ALIGN_VAR_STACK(__gc_var_stack__, start);
END_XFORM_SKIP;
} else
b->cont = NULL;
/* In 3m-mode, we need `start' at the end of the frame */
PAST_VAR_STACK(start);
/* b is a pointer into the middle of `base', which bad for precise
gc, so we hide it. */

View File

@ -4,7 +4,11 @@
* things that should be defined here.
*/
/* These are not used on Windows. */
#ifndef __MZSCHEME_CONFIGURATION_INFO__
#define __MZSCHEME_CONFIGURATION_INFO__
/* Undefined items are not used on Windows. */
/* The size of a `char', as computed by sizeof. */
#undef SIZEOF_CHAR
@ -21,9 +25,14 @@
/* The size of a `long long', as computed by sizeof. */
#undef SIZEOF_LONG_LONG
/* Direction of stack growth: 1 = up, -1 = down, 0 = unknown */
#define STACK_DIRECTION -1
/* whether nl_langinfo works */
#undef HAVE_CODESET
/* whether getaddrinfo works */
#define HAVE_GETADDRINFO 1
#endif