diff --git a/racket/src/README b/racket/src/README index 2e19fa02a1..ebe1d2e2fd 100644 --- a/racket/src/README +++ b/racket/src/README @@ -29,9 +29,7 @@ To compile with MinGW tools, follow the Unix instructions below; do not use `--enable-shared', because DLLs will be generated automatically. The result is a Windows-style build, but without MzCOM. If you are using a variant of MinGW without "libdelayimp.a", get the implementation of -"delayimp.c" from MinGW-w64 and compile it to "libdelayimp.a". When -compiling with MinGW-w64 for 64-bit mode, the `--enable-sgc' flag -to `configure' is currently required. +"delayimp.c" from MinGW-w64 and compile it to "libdelayimp.a". To compile with Cygwin tools, follow the Unix instructions below, and be sure to configure with `--enable-shared'. The result is a Unix-style @@ -286,17 +284,6 @@ Cross-compilation requires at least two flags to `configure': This flag is needed because building and installing Racket requires running (an intermediate version of) Racket. -A third `configure' flag is typical: - - * `--enable-sgc', which uses a simpler garbage collector for the - intermediate variant of Racket that is normally used only to build - the final variant (see CGC vs 3m below). - - Otherwise, you may need to set CC_FOR_BUILD to a compiler for the - build platform, so that helper executables can be created in the - process of building the intermediate Racket that is used to build - the final Racket. - Some less commonly needed `configure' flags: * `--enable-stackup', if the target platform's stack grows up. @@ -312,7 +299,6 @@ the NDK, use (all on one line) configure --host=arm-linux-androideabi --enable-sysroot="[ndk]/platforms/android-[N]/arch-arm" - --enable-sgc --enable-racket=racket where [ndk] is the path to the installed NDK, [N] is a target version @@ -385,33 +371,29 @@ documentation for "config search paths" for more information. ======================================================================== At a minimum, to port Racket to a new platform, edit "racket/sconfig.h" -to provide a platform-specific compilation information. As distributed, -"racket/sconfig.h" contains configurations for the following platforms: - - Windows (x86, x86_64) - Mac OS X (PPC, x86, x86_64) - Linux (x86, x86_64, PPC, 68k) - Cygwin (x86) - Solaris (x86, Sparc) - FreeBSD (x86, x86_64) - OpenBSD (x86) - NetBSD (x86) - -If your platform is not supported by the Boehm garbage collector -(distributed with Racket source), provide the `--enable-sgc' flag to -`configure'. +to provide a platform-specific compilation information. ======================================================================== Additional Compilation Notes ======================================================================== -Garbage Collector +CGC Build Options ----------------- -The conservative garbage collector distributed with Racket (in the "gc" -directory) has been modified slightly from Boehm's standard -distribution. Mostly, the change modify the way that object -finalization is handled. +As noted above in "CGC versus 3m", Racket builds a CGC variant in the +process of creating the normal 3m variant. Within the CGC variant, two +implementations are possible. + +By default, Racket CGC is implemented with SenoraGC (in the "sgc" +directory), which is relativey portable. Provide `--disable-sgc` to +instead use the Boehm GC (in the "gc" directory), which should perform +better and was the default for Racket CGC through version 6.1. + +The variant of the Boehm GC that is included with Racket has been +modified slightly from Boehm's standard distribution; mostly, the +changes modify the way that object finalization is handled. + +[Currently, the Windows build still uses the Boehm GC by default.] Floating point, x87, SSE, Extflonums, and the JIT ------------------------------------------------- diff --git a/racket/src/configure b/racket/src/configure index 59ea436074..3ffd8dd863 100755 --- a/racket/src/configure +++ b/racket/src/configure @@ -1456,8 +1456,8 @@ Optional Features: --enable-macprefix allow --prefix with a Mac OS X install --enable-mac64 allow 64-bit Mac OS X build (enabled by default) --enable-cgcdefault use CGC as default build (NOT RECOMMENDED) - --enable-sgc use Senora GC instead of the Boehm GC - --enable-sgcdebug use Senora GC for debugging + --enable-sgc use Senora GC instead of the Boehm GC (enabled by default) + --enable-sgcdebug use Senora GC for debugging (expensive debug mode) --enable-backtrace 3m: support GC backtrace dumps (expensive debug mode) --enable-pthread link with pthreads (usually auto-enabled if needed) --enable-stackup assume "up" if stack direction cannot be determined @@ -2738,6 +2738,8 @@ fi # Check whether --enable-sgc was given. if test "${enable_sgc+set}" = set; then : enableval=$enable_sgc; +else + enable_sgc=yes fi # Check whether --enable-sgcdebug was given. @@ -3007,7 +3009,7 @@ show_explicitly_disabled "${enable_places}" Places show_explicitly_enabled "${enable_futures}" Futures show_explicitly_disabled "${enable_futures}" Futures -show_explicitly_enabled "${enable_sgc}" SGC +show_explicitly_disabled "${enable_sgc}" SGC show_explicitly_enabled "${enable_sgcdebug}" "SGC debug mode" show_explicitly_enabled "${enable_backtrace}" "3m GC backtraces" "Note that this mode is not intended for normal Racket use" @@ -5496,8 +5498,8 @@ $as_echo_n "checking $msg... " >&6; } #include int main() { void *p; - p = mmap(0, 2 << 16, PROT_READ | PROT_WRITE | PROT_EXEC, MAP_PRIVATE, open("/dev/zero", O_RDWR), 0); - mprotect(p, 2 << 16, PROT_READ | PROT_WRITE | PROT_EXEC); + p = mmap(0, 2 << 16, PROT_READ | PROT_WRITE, MAP_PRIVATE, open("/dev/zero", O_RDWR), 0); + mprotect(p, 2 << 16, PROT_READ | PROT_WRITE); return 0; } _ACEOF @@ -5515,6 +5517,36 @@ $as_echo "$use_mprotect" >&6; } $as_echo "#define HAVE_MMAP_MPROTECT 1" >>confdefs.h fi + + if test "${use_mprotect}" = "yes" && test "${enable_sgc}" != "yes" ; then + msg="mprotect with PROT_EXEC" + { $as_echo "$as_me:${as_lineno-$LINENO}: checking $msg" >&5 +$as_echo_n "checking $msg... " >&6; } + cat confdefs.h - <<_ACEOF >conftest.$ac_ext +/* end confdefs.h. */ + + #include + #include + int main() { + void *p; + p = mmap(0, 2 << 16, PROT_READ | PROT_WRITE, MAP_PRIVATE, open("/dev/zero", O_RDWR), 0); + if (mprotect(p, 2 << 16, PROT_READ | PROT_WRITE | PROT_EXEC)) return 1; + return 0; + } +_ACEOF +if ac_fn_c_try_link "$LINENO"; then : + can_mprotect_exec=yes +else + can_mprotect_exec=no +fi +rm -f core conftest.err conftest.$ac_objext \ + conftest$ac_exeext conftest.$ac_ext + { $as_echo "$as_me:${as_lineno-$LINENO}: result: $can_mprotect_exec" >&5 +$as_echo "$can_mprotect_exec" >&6; } + if test "${can_mprotect_exec}" = "no" ; then + echo "Senora GC is required due to mprotect() failure" + fi + fi fi if test "${check_page_size}" = "yes" ; then diff --git a/racket/src/racket/configure.ac b/racket/src/racket/configure.ac index a37a060234..c30a681c38 100644 --- a/racket/src/racket/configure.ac +++ b/racket/src/racket/configure.ac @@ -66,8 +66,8 @@ AC_ARG_ENABLE(macprefix, [ --enable-macprefix allow --prefix with a Mac OS AC_ARG_ENABLE(mac64, [ --enable-mac64 allow 64-bit Mac OS X build (enabled by default)], , enable_mac64=yes) AC_ARG_ENABLE(cgcdefault, [ --enable-cgcdefault use CGC as default build (NOT RECOMMENDED)]) -AC_ARG_ENABLE(sgc, [ --enable-sgc use Senora GC instead of the Boehm GC]) -AC_ARG_ENABLE(sgcdebug,[ --enable-sgcdebug use Senora GC for debugging]) +AC_ARG_ENABLE(sgc, [ --enable-sgc use Senora GC instead of the Boehm GC (enabled by default)], , enable_sgc=yes) +AC_ARG_ENABLE(sgcdebug,[ --enable-sgcdebug use Senora GC for debugging (expensive debug mode)]) AC_ARG_ENABLE(backtrace, [ --enable-backtrace 3m: support GC backtrace dumps (expensive debug mode)]) AC_ARG_ENABLE(pthread, [ --enable-pthread link with pthreads (usually auto-enabled if needed)]) @@ -298,7 +298,7 @@ show_explicitly_disabled "${enable_places}" Places show_explicitly_enabled "${enable_futures}" Futures show_explicitly_disabled "${enable_futures}" Futures -show_explicitly_enabled "${enable_sgc}" SGC +show_explicitly_disabled "${enable_sgc}" SGC show_explicitly_enabled "${enable_sgcdebug}" "SGC debug mode" show_explicitly_enabled "${enable_backtrace}" "3m GC backtraces" "Note that this mode is not intended for normal Racket use" @@ -1104,14 +1104,32 @@ if test "${check_for_mprotect}" = "yes" ; then #include int main() { void *p; - p = mmap(0, 2 << 16, PROT_READ | PROT_WRITE | PROT_EXEC, MAP_PRIVATE, open("/dev/zero", O_RDWR), 0); - mprotect(p, 2 << 16, PROT_READ | PROT_WRITE | PROT_EXEC); + p = mmap(0, 2 << 16, PROT_READ | PROT_WRITE, MAP_PRIVATE, open("/dev/zero", O_RDWR), 0); + mprotect(p, 2 << 16, PROT_READ | PROT_WRITE); return 0; }])], use_mprotect=yes, use_mprotect=no) AC_MSG_RESULT($use_mprotect) if test "${use_mprotect}" = "yes" ; then AC_DEFINE(HAVE_MMAP_MPROTECT,1,[Have mmap and mprotect]) fi + + if test "${use_mprotect}" = "yes" && test "${enable_sgc}" != "yes" ; then + [ msg="mprotect with PROT_EXEC" ] + AC_MSG_CHECKING($msg) + AC_LINK_IFELSE([AC_LANG_SOURCE([ + #include + #include + int main() { + void *p; + p = mmap(0, 2 << 16, PROT_READ | PROT_WRITE, MAP_PRIVATE, open("/dev/zero", O_RDWR), 0); + if (mprotect(p, 2 << 16, PROT_READ | PROT_WRITE | PROT_EXEC)) return 1; + return 0; + }])], can_mprotect_exec=yes, can_mprotect_exec=no) + AC_MSG_RESULT($can_mprotect_exec) + if test "${can_mprotect_exec}" = "no" ; then + echo "Senora GC is required due to mprotect() failure" + fi + fi fi if test "${check_page_size}" = "yes" ; then diff --git a/racket/src/racket/sgc/README b/racket/src/racket/sgc/README index 6f0e13cd62..be5db5a159 100644 --- a/racket/src/racket/sgc/README +++ b/racket/src/racket/sgc/README @@ -1,17 +1,15 @@ SenoraGC is a relatively portable conservative GC for a slightly -cooperative environment. +cooperative environment. Its API is based on the Boehm GC. -The collector is intended mainly for debugging and memory tracing, but -it can also act as a reasonbaly efficient, general-purpose, -conservative collector. The standard Racket build uses SGC for -certain platforms where Boehm's GC hasn't been ported, yet (notably, -OSKit and BeOS). +The collector was originally intended for debugging and memory +tracing, but it can also act as a reasonbaly efficient, +general-purpose, conservative collector. -This collector is not recommended as a replacement for Boehm's GC if -you can get Boehm's to work at all. SenoraGC MIGHT be useful if, for -some reason, Boehm's collector does not work for your platform. -SenoraGC MIGHT be useful as a debugging collector if you can figure -out the [undocumented] debugging utilities. +If you intend to use the CGC variant of Racket instead of the (usual) +3m variant, then instead of SenoraGC, consider using the variant of +the Boehm GC that is distributed with Racket; it should perform +significantly better. Enable the Boehm GC by providing `--disable-sgc` +to `configure`. Usage: @@ -24,6 +22,6 @@ actually done automatically for static variables, but it can't be done portably in general. (See AUTO_STATIC_ROOTS_IF_POSSIBLE in the flags section.) -GC space is allocated using malloc() and free(). Alternatively, the GC -can define malloc() and free() itself if platform-specific allocation -routines are supported. +GC space is allocated using mmap() where available, malloc() +otherwise. The GC can define malloc() and free() itself if +platform-specific allocation routines are supported. diff --git a/racket/src/racket/sgc/sgc.c b/racket/src/racket/sgc/sgc.c index 4d4266d481..1d1079348b 100644 --- a/racket/src/racket/sgc/sgc.c +++ b/racket/src/racket/sgc/sgc.c @@ -315,8 +315,9 @@ /* SECTOR_SEGMENT_SIZE determines the alignment of collector blocks. Since it should be a power of 2, LOG_SECTOR_SEGMENT_SIZE is specified directly. A larger block size speeds up GC, but wastes - more unallocated bytes in same-size buckets. */ -#define LOG_SECTOR_SEGMENT_SIZE 14 + more unallocated bytes in same-size buckets. The block size must + be at least as large as the OS's page size. */ +#define LOG_SECTOR_SEGMENT_SIZE 16 #define SECTOR_SEGMENT_SIZE (1 << LOG_SECTOR_SEGMENT_SIZE) #define SECTOR_SEGMENT_MASK (~(SECTOR_SEGMENT_SIZE-1)) @@ -328,7 +329,7 @@ /* Number of sector segments to be allocated at once with malloc() to avoid waste when obtaining the proper alignment. */ -#define SECTOR_SEGMENT_GROUP_SIZE 32 +#define SECTOR_SEGMENT_GROUP_SIZE 16 /* Number of bits used in 32-bit level table for checking existence of a sector. Creates a table of (1 << SECTOR_LOOKUP_SHIFT) pointers @@ -989,6 +990,10 @@ static void *ofm_malloc_zero(size_t len) return mmap_sector((len >> LOG_SECTOR_SEGMENT_SIZE) + 1, 0); } +/* Instead of calling mmap()/unmap() every time we need to + allocate/free a sector, use the allocation-cache layer from + "gc2" for non-executable pages: */ + # define APAGE_SIZE SECTOR_SEGMENT_SIZE # define NO_ALLOC_CACHE_FREE # include "../gc2/my_qsort.c" diff --git a/racket/src/racket/src/string.c b/racket/src/racket/src/string.c index e770f84bbb..f1fdb172c0 100644 --- a/racket/src/racket/src/string.c +++ b/racket/src/racket/src/string.c @@ -2086,9 +2086,9 @@ char *scheme_version(void) # define VERSION_SUFFIX "" #else # ifdef USE_SENORA_GC -# define VERSION_SUFFIX " [cgc~]" -# else # define VERSION_SUFFIX " [cgc]" +# else +# define VERSION_SUFFIX " [cgc/b]" # endif #endif diff --git a/racket/src/worksp/README b/racket/src/worksp/README index 52d8811b25..ea7379c052 100644 --- a/racket/src/worksp/README +++ b/racket/src/worksp/README @@ -68,7 +68,7 @@ racket\src\README if you don't know about the two variants.) If you can't run "build.bat" or don't want to, you have to perform -several steps: first builg RacketCGC, then build Racket3m, etc. +several steps: first build RacketCGC, then build Racket3m, etc. Building RacketCGC and GRacketCGC ---------------------------------