From: Matthew Mondor Date: Fri, 11 Sep 2015 20:54:18 +0000 (-0400) Subject: - User-defined heap sizes can now exceed the size of a fixnum on 32-bit X-Git-Url: http://git.pulsar-zone.net/?a=commitdiff_plain;h=c5c606cc010b6fb276195cffecd5a59d1a4b702e;p=ecl.git - User-defined heap sizes can now exceed the size of a fixnum on 32-bit Fixes issue #140 - The heap size limit was intended to be 1GB on 32-bit or 4GB on 64-bit but inconsistency between ECL_FIXNUM_BITS and FIXNUM_BITS in the code prevented the heap to grow for 64-bit. This now occurs, and a few other less visible bugs were fixed by restoring consistency to ECL_FIXNUM_BITS. --- diff --git a/CHANGELOG b/CHANGELOG index 0409531..9e99b15 100644 --- a/CHANGELOG +++ b/CHANGELOG @@ -37,7 +37,7 @@ mp:mailbox-try-send (non-blocking) - Added back removed C interfaces - ecl_improt_current_thread + ecl_import_current_thread ecl_release_current_thread ** Enhancements: @@ -62,6 +62,14 @@ - Generated C code works well with IEEE 754 infinities (regression tests created) + - User-defined heap sizes can now exceed the size of a fixnum on 32-bit + + - The heap size limit was intended to be 1GB on 32-bit or 4GB on 64-bit + but inconsistency between ECL_FIXNUM_BITS and FIXNUM_BITS in the code + prevented the heap to grow for 64-bit. This now occurs, and a few + other less visible bugs were fixed by restoring consistency to + ECL_FIXNUM_BITS. + - EXT:EXTERNAL-PROCESS-WAIT potential race condition fix * 16.0.0 changes since 15.3.7 diff --git a/src/c/alloc_2.d b/src/c/alloc_2.d index cba7ba7..f9f98ca 100644 --- a/src/c/alloc_2.d +++ b/src/c/alloc_2.d @@ -72,7 +72,7 @@ extern void GC_init_explicit_typing(void); **********************************************************/ void -_ecl_set_max_heap_size(cl_index new_size) +_ecl_set_max_heap_size(size_t new_size) { const cl_env_ptr the_env = ecl_process_env(); ecl_disable_interrupts_env(the_env); diff --git a/src/c/main.d b/src/c/main.d index 81baac5..b341faf 100755 --- a/src/c/main.d +++ b/src/c/main.d @@ -62,6 +62,18 @@ const char *ecl_self; /************************ GLOBAL INITIALIZATION ***********************/ + +/* HEAP */ + +#if ECL_FIXNUM_BITS <= 32 +/* 1GB */ +#define HEAP_SIZE_DEFAULT 1073741824L +#else +/* 4GB */ +#define HEAP_SIZE_DEFAULT 4294967296L +#endif + + static int ARGC; static char **ARGV; cl_fixnum ecl_option_values[ECL_OPT_LIMIT+1] = { @@ -90,11 +102,7 @@ cl_fixnum ecl_option_values[ECL_OPT_LIMIT+1] = { 128*sizeof(cl_index)*1024, /* ECL_OPT_C_STACK_SIZE */ 4*sizeof(cl_index)*1024, /* ECL_OPT_C_STACK_SAFETY_AREA */ 1, /* ECL_OPT_SIGALTSTACK_SIZE */ -#if ECL_FIXNUM_BITS <= 32 - 1024*1024*1024, /* ECL_OPT_HEAP_SIZE */ -#else - 4294967296L, /* ECL_OPT_HEAP_SIZE */ -#endif + HEAP_SIZE_DEFAULT, /* ECL_OPT_HEAP_SIZE */ 1024*1024, /* ECL_OPT_HEAP_SAFETY_AREA */ 0, /* ECL_OPT_THREAD_INTERRUPT_SIGNAL */ 1, /* ECL_OPT_SET_GMP_MEMORY_FUNCTIONS */ diff --git a/src/c/stacks.d b/src/c/stacks.d index 2cecf1a..e71a02f 100644 --- a/src/c/stacks.d +++ b/src/c/stacks.d @@ -621,21 +621,30 @@ cl_object si_set_limit(cl_object type, cl_object limit) { cl_env_ptr env = ecl_process_env(); - cl_index the_size = ecl_to_size(limit); cl_index margin; if (type == @'ext::frame-stack') { + cl_index the_size = ecl_to_size(limit); margin = ecl_option_values[ECL_OPT_FRAME_STACK_SAFETY_AREA]; frs_set_size(env, the_size + 2*margin); } else if (type == @'ext::binding-stack') { + cl_index the_size = ecl_to_size(limit); margin = ecl_option_values[ECL_OPT_BIND_STACK_SAFETY_AREA]; ecl_bds_set_size(env, the_size + 2*margin); } else if (type == @'ext::c-stack') { + cl_index the_size = ecl_to_size(limit); margin = ecl_option_values[ECL_OPT_C_STACK_SAFETY_AREA]; cs_set_size(env, the_size + 2*margin); - } else if (type == @'ext::lisp-stack') + } else if (type == @'ext::lisp-stack') { + cl_index the_size = ecl_to_size(limit); ecl_stack_set_size(env, the_size); - else + } else { + /* + * size_t can be larger than cl_index, and ecl_to_size() + * creates a fixnum which is too small for size_t on 32-bit. + */ + size_t the_size = (size_t)ecl_to_ulong(limit); _ecl_set_max_heap_size(the_size); + } return si_get_limit(type); } @@ -654,7 +663,8 @@ si_get_limit(cl_object type) else if (type == @'ext::lisp-stack') output = env->stack_limit_size; else - output = cl_core.max_heap_size; + /* size_t can be larger than cl_index */ + @(return ecl_make_unsigned_integer(cl_core.max_heap_size)); @(return ecl_make_unsigned_integer(output)) } diff --git a/src/h/external.h b/src/h/external.h index 6a53588..661b6cf 100755 --- a/src/h/external.h +++ b/src/h/external.h @@ -232,7 +232,7 @@ struct cl_core_struct { #endif cl_object libraries; - cl_index max_heap_size; + size_t max_heap_size; cl_object bytes_consed; cl_object gc_counter; bool gc_stats; diff --git a/src/h/internal.h b/src/h/internal.h index 0b24cf1..a39d918 100755 --- a/src/h/internal.h +++ b/src/h/internal.h @@ -60,7 +60,7 @@ extern void _ecl_dealloc_env(cl_env_ptr); #ifdef GBC_BOEHM #define ECL_COMPACT_OBJECT_EXTRA(x) ((void*)((x)->array.displaced)) #endif -extern void _ecl_set_max_heap_size(cl_index new_size); +extern void _ecl_set_max_heap_size(size_t new_size); extern cl_object ecl_alloc_bytecodes(cl_index data_size, cl_index code_size); extern cl_index ecl_object_byte_size(cl_type t); diff --git a/src/lsp/top.lsp b/src/lsp/top.lsp index 5f4aa16..4f59ae2 100644 --- a/src/lsp/top.lsp +++ b/src/lsp/top.lsp @@ -404,8 +404,8 @@ The top-level loop of ECL. It is called by default when ECL is invoked." (ext:lisp-implementation-vcs-id)) (format t "~%Copyright (C) 1984 Taiichi Yuasa and Masami Hagiya~@ Copyright (C) 1993 Giuseppe Attardi~@ -Copyright (C) 2000 Juan J. Garcia-Ripoll -Copyright (C) 2015 Daniel Kochmanski +Copyright (C) 2000 Juan J. Garcia-Ripoll~@ +Copyright (C) 2015 Daniel Kochmanski~@ ECL is free software, and you are welcome to redistribute it~@ under certain conditions; see file 'Copyright' for details.") (format *standard-output* "~%Type :h for Help. "))