summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--HACKING96
-rw-r--r--buf.c5
-rwxr-xr-xconfigure5
-rw-r--r--eval.c6
-rw-r--r--ffi.c10
-rw-r--r--gc.c18
-rw-r--r--hash.c3
-rw-r--r--lib.c79
-rw-r--r--linenoise/linenoise.c3
-rw-r--r--parser.c5
-rw-r--r--regex.c6
-rw-r--r--signal.c2
-rw-r--r--stream.c4
-rw-r--r--struct.c18
-rw-r--r--sysif.c22
-rw-r--r--time.c6
-rw-r--r--tree.c44
-rw-r--r--unwind.c3
-rw-r--r--unwind.h17
-rw-r--r--vm.c14
20 files changed, 215 insertions, 151 deletions
diff --git a/HACKING b/HACKING
index 9544d114..caa7501c 100644
--- a/HACKING
+++ b/HACKING
@@ -8,40 +8,40 @@ SECTION LINE
0. Overview 47
1. Coding Practice 54
-1.2 Program File Structure 77
-1.3 Style 91
-1.3 Error Handling 153
-1.4 I/O 166
-1.5 Type Safety 176
-1.6 Regression 218
-
-2. Dynamic Types 227
-2.1 Two Kinds of Values 234
-2.1 Pointer Bitfield 245
-2.2 Heap Objects 268
-2.3 The COBJ type 288
-2.4 Strings 305
-2.4.1 Encapsulated C Strings 320
-2.4.2 Representation Hacks for 2-byte wchar_t 364
-
-3. Garbage Collection 423
-3.1 Root Pointers 441
-3.2 GC-safe Code 464
-3.2.1 Rule One: Full Initialization 490
-3.2.2 Rule Two: Make it Reachable 519
-3.3 Weak Reference Support 707
-3.4 Finalization 750
-3.5 Generational GC 774
-3.5.2 Representation of Generations 783
-3.5.3 Basic Algorithm 819
-3.5.4 Handling Backpointers 854
-3.5.5 Generational GC and Finalization 932
-
-4. Debugging 961
-4.2. Debugging the Yacc-generated Parser 1092
-4.3. Debugging GC Issues 1105
-4.4 Object Breakpoint 1128
-4.5 Valgrind: Your Friend 1147
+1.2 Program File Structure 95
+1.3 Style 109
+1.3 Error Handling 171
+1.4 I/O 184
+1.5 Type Safety 194
+1.6 Regression 236
+
+2. Dynamic Types 245
+2.1 Two Kinds of Values 252
+2.1 Pointer Bitfield 263
+2.2 Heap Objects 286
+2.3 The COBJ type 306
+2.4 Strings 323
+2.4.1 Encapsulated C Strings 338
+2.4.2 Representation Hacks for 2-byte wchar_t 382
+
+3. Garbage Collection 441
+3.1 Root Pointers 459
+3.2 GC-safe Code 482
+3.2.1 Rule One: Full Initialization 508
+3.2.2 Rule Two: Make it Reachable 537
+3.3 Weak Reference Support 725
+3.4 Finalization 768
+3.5 Generational GC 792
+3.5.2 Representation of Generations 801
+3.5.3 Basic Algorithm 837
+3.5.4 Handling Backpointers 872
+3.5.5 Generational GC and Finalization 950
+
+4. Debugging 979
+4.2. Debugging the Yacc-generated Parser 1110
+4.3. Debugging GC Issues 1123
+4.4 Object Breakpoint 1146
+4.5 Valgrind: Your Friend 1165
0. Overview
@@ -56,11 +56,29 @@ provide rationale and make coding recommendations.
1.1 Language
Txr is written in a language that consists of the common dialect between C90
-and C++98. The code can be built with either the GNU C compiler or the GNU C++
-compiler. Use is made of some Unix functions from before Unix95, which are
-requested by means of -D_XOPEN_SOURCE (POSIX.1, POSIX.2, X/Open Portability
-Guide 4). Also, the <wchar.h> header is used, which was introduced by a 1995
-addendum to the C language, so it may be said that the actual C dialect is C95.
+and C++98, with some GCC extensions, such as:
+
+- initializing structure members with values not computable at load-time
+- converting between object and function pointers
+- certain extensions detected by the configure script as working, such
+ as the long long type
+- bitfields of an enum type rather than int.
+
+The code can be built with either the GNU C compiler or the GNU C++
+compiler.
+
+Use is made of numerous library functions which are detected by the configure
+script without regard for dialect. For instance, some C99 mathematics functions
+are used, if available, as well as numerous POSIX functions. Effectively, these
+can be regarded as extensions to the C90 language, since they are revealed in
+the headers and library linkage.
+
+The <inttypes.h> header isn't used, though there is a reference to it in
+the Flex-generated scanner, active only if that is compiled in C99 mode.
+
+The <wchar.h> header is used, which was introduced by a 1995 addendum to the C
+language, so it may be said that the actual C dialect is C95 with some
+extensions.
In coding new features or fixing bugs, care must be taken to preserve this.
Code must continue to compile as C and C++, and not increase the portability
diff --git a/buf.c b/buf.c
index 1328698f..932063a3 100644
--- a/buf.c
+++ b/buf.c
@@ -351,10 +351,11 @@ val replace_buf(val buf, val items, val from, val to)
memmove(buf->b.data + c_num(from, self), items->b.data, c_num(len_it, self));
} else {
seq_iter_t item_iter;
- seq_iter_init(self, &item_iter, items);
cnum f = c_num(from, self);
cnum t = c_num(to, self);
+ seq_iter_init(self, &item_iter, items);
+
for (; f != t; f++) {
val item = seq_geti(&item_iter);
buf_put_uchar(buf, num(f), item);
@@ -367,7 +368,7 @@ val replace_buf(val buf, val items, val from, val to)
val buf_list(val list)
{
- val self = lit("buf-list");;
+ val self = lit("buf-list");
val len = length(list);
val buf = make_buf(zero, zero, len);
seq_iter_t iter;
diff --git a/configure b/configure
index 5365701e..561976e6 100755
--- a/configure
+++ b/configure
@@ -167,8 +167,8 @@ nm='$(cross)$(tool_prefix)nm'
opt_flags='-O2 -fno-stack-protector'
lang_flags='-D_XOPEN_SOURCE=700 -D_POSIX_C_SOURCE=200112 -D_GNU_SOURCE'
diag_flags="-Wall -Wextra -Werror=implicit-function-declaration \
- -Werror=missing-prototypes -Werror=strict-prototypes \
- -Werror=old-style-definition"
+ -Werror=missing-prototypes -Werror=strict-prototypes -Werror=vla \
+ -Werror=old-style-definition -Werror=declaration-after-statement"
debug_flags=-g
debug_only_flags=-DTXR_DEBUG
debug_also=
@@ -810,6 +810,7 @@ if [ $cplusplus ] ; then
diag_flags=''
for flag in "$@" ; do
case $flag in
+ *=declaration-after-statement | \
*=implicit-function-declaration | \
*=missing-prototypes | \
*=old-style-* | \
diff --git a/eval.c b/eval.c
index 7517eb8b..e07d5327 100644
--- a/eval.c
+++ b/eval.c
@@ -2670,11 +2670,12 @@ static val op_dohash(val form, val env)
val valvar = cons(valsym, nil);
val new_env = make_env(cons(keyvar, cons(valvar, nil)), nil, env);
val cell;
+ val result = nil;
struct hash_iter hi;
hash_iter_init(&hi, eval(hashform, env, hashform), op);
- uw_block_begin (nil, result);
+ uw_block_beg (nil, result);
while ((cell = hash_iter_next(&hi)) != nil) {
/* These assignments are gc-safe, because keyvar and valvar
@@ -3125,8 +3126,9 @@ static val op_upenv(val form, val env)
static val op_load_time_lit(val form, val env)
{
- (void) env;
val args = cdr(form);
+ (void) env;
+
if (car(args)) {
return cadr(args);
} else {
diff --git a/ffi.c b/ffi.c
index a383c831..767d7a9b 100644
--- a/ffi.c
+++ b/ffi.c
@@ -509,17 +509,17 @@ static val ffi_void_get(struct txr_ffi_type *tft, mem_t *src, val self)
static void ffi_simple_release(struct txr_ffi_type *tft, val obj,
mem_t *dst, val self)
{
+ mem_t **loc = coerce(mem_t **, dst);
(void) tft;
(void) obj;
(void) self;
- mem_t **loc = coerce(mem_t **, dst);
free(*loc);
*loc = 0;
}
#if __i386__ || __x86_64__ || __PPC64__ || __ARM_FEATURE_UNALIGNED
-#define align_sw_get(type, src)
+#define align_sw_get(type, src) enum { dummy ## __LINE__ }
#define align_sw_end
#define align_sw_put_end
#define align_sw_put(type, dst, expr) (expr)
@@ -531,7 +531,7 @@ static void ffi_simple_release(struct txr_ffi_type *tft, val obj,
const size_t sz = sizeof (type); \
mem_t *src_prev = src; \
mem_t *buf = al ? src : convert(mem_t *, alloca(sz)); \
- mem_t *src = al ? buf : (memcpy(buf, src_prev, sz), buf);
+ mem_t *src = al ? buf : (memcpy(buf, src_prev, sz), buf)
#define align_sw_end \
}
@@ -557,8 +557,8 @@ static void ffi_simple_release(struct txr_ffi_type *tft, val obj,
#if HAVE_I8
static void ffi_i8_put(struct txr_ffi_type *tft, val n, mem_t *dst, val self)
{
- (void) tft;
i8_t v = c_i8(n, self);
+ (void) tft;
*coerce(i8_t *, dst) = v;
}
@@ -571,8 +571,8 @@ static val ffi_i8_get(struct txr_ffi_type *tft, mem_t *src, val self)
static void ffi_u8_put(struct txr_ffi_type *tft, val n, mem_t *dst, val self)
{
- (void) tft;
u8_t v = c_u8(n, self);
+ (void) tft;
*coerce(u8_t *, dst) = v;
}
diff --git a/gc.c b/gc.c
index da5feb70..8b0ebf57 100644
--- a/gc.c
+++ b/gc.c
@@ -914,14 +914,16 @@ void gc_init(val *stack_bottom)
gc_stack_bottom = stack_bottom;
gc_stack_limit = gc_stack_bottom - DFL_STACK_LIMIT / sizeof (val);
#if HAVE_RLIMIT
- struct rlimit rl;
- if (getrlimit(RLIMIT_STACK, &rl) == 0) {
- rlim_t lim = rl.rlim_cur;
- if (lim != RLIM_INFINITY) {
- ptrdiff_t delta = (lim >= MIN_STACK_LIMIT
- ? (lim - lim / 16)
- : MIN_STACK_LIMIT) / sizeof (val);
- gc_stack_limit = gc_stack_bottom - delta;
+ {
+ struct rlimit rl;
+ if (getrlimit(RLIMIT_STACK, &rl) == 0) {
+ rlim_t lim = rl.rlim_cur;
+ if (lim != RLIM_INFINITY) {
+ ptrdiff_t delta = (lim >= MIN_STACK_LIMIT
+ ? (lim - lim / 16)
+ : MIN_STACK_LIMIT) / sizeof (val);
+ gc_stack_limit = gc_stack_bottom - delta;
+ }
}
}
#endif
diff --git a/hash.c b/hash.c
index ccc10507..56533556 100644
--- a/hash.c
+++ b/hash.c
@@ -2096,6 +2096,8 @@ void hash_early_init(void)
void hash_init(void)
{
+ val ghu = func_n1(get_hash_userdata);
+
weak_keys_k = intern(lit("weak-keys"), keyword_package);
weak_vals_k = intern(lit("weak-vals"), keyword_package);
weak_and_k = intern(lit("weak-and"), keyword_package);
@@ -2105,7 +2107,6 @@ void hash_init(void)
eq_based_k = intern(lit("eq-based"), keyword_package);
userdata_k = intern(lit("userdata"), keyword_package);
hash_seed_s = intern(lit("*hash-seed*"), user_package);
- val ghu = func_n1(get_hash_userdata);
hash_cls->cls_sym = hash_s;
hash_iter_cls->cls_sym = hash_iter_s;
diff --git a/lib.c b/lib.c
index a82bdea7..0543d9dd 100644
--- a/lib.c
+++ b/lib.c
@@ -2256,9 +2256,10 @@ static val revlist(val in, val *tail)
loc list_collect_revappend(loc ptail, val obj)
{
val last;
- obj = nullify(obj);
val tailobj = deref(ptail);
+ obj = nullify(obj);
+
again:
switch (type(tailobj)) {
case CONS:
@@ -2520,10 +2521,11 @@ static val sub_iter(val obj, val from, val to)
{
val self = lit("sub");
seq_iter_t iter;
- seq_iter_init(self, &iter, obj);
val idx = zero, elem;
list_collect_decl (out, ptail);
+ seq_iter_init(self, &iter, obj);
+
if (from == t)
return nil;
@@ -5443,10 +5445,11 @@ val replace_str(val str_in, val items, val from, val to)
c_str(items, self), c_num(len_it, self));
} else {
seq_iter_t item_iter;
- seq_iter_init(self, &item_iter, items);
cnum f = c_num(from, self);
cnum t = c_num(to, self);
+ seq_iter_init(self, &item_iter, items);
+
for (; f != t; f++)
str_in->st.str[f] = c_chr(seq_geti(&item_iter));
}
@@ -6719,9 +6722,9 @@ val make_sym(val name)
}
}
-val gensym(val prefix)
+val gensym(val prefix_in)
{
- prefix = default_arg(prefix, lit("g"));
+ val prefix = default_arg(prefix_in, lit("g"));
loc gs_loc = lookup_var_l(nil, gensym_counter_s);
val name = format(nil, lit("~a~,04d"), prefix,
set(gs_loc, plus(deref(gs_loc), one)), nao);
@@ -9220,11 +9223,12 @@ val replace_vec(val vec_in, val items, val from, val to)
mut(vec_in);
} else {
seq_iter_t item_iter;
- seq_iter_init(self, &item_iter, items);
int mut_needed = 0;
cnum f = c_num(from, self);
cnum t = c_num(to, self);
+ seq_iter_init(self, &item_iter, items);
+
for (; f != t; f++) {
val item = seq_geti(&item_iter);
if (is_ptr(item))
@@ -10126,10 +10130,11 @@ val mapcar_listout(val fun, val seq)
{
val self = lit("mapcar");
seq_iter_t iter;
- seq_iter_init(self, &iter, seq);
val elem;
list_collect_decl (out, ptail);
+ seq_iter_init(self, &iter, seq);
+
while (seq_get(&iter, &elem))
ptail = list_collect(ptail, funcall1(fun, elem));
@@ -10158,10 +10163,11 @@ val mappend(val fun, val seq)
{
val self = lit("mappend");
seq_iter_t iter;
- seq_iter_init(self, &iter, seq);
val elem;
list_collect_decl (out, ptail);
+ seq_iter_init(self, &iter, seq);
+
while (seq_get(&iter, &elem))
ptail = list_collect_append(ptail, funcall1(fun, elem));
@@ -10172,9 +10178,10 @@ val mapdo(val fun, val seq)
{
val self = lit("mapdo");
seq_iter_t iter;
- seq_iter_init(self, &iter, seq);
val elem;
+ seq_iter_init(self, &iter, seq);
+
while (seq_get(&iter, &elem))
funcall1(fun, elem);
@@ -10239,9 +10246,11 @@ static val window_map_list(val range, val boundary, val fun, val list,
args->arg[i] = ref(boundary, num(j++));
for (;;) {
+ val item;
args_decl (args_cp, ws);
args_copy(args_cp, args);
- val item = generic_funcall(fun, args_cp);
+
+ item = generic_funcall(fun, args_cp);
switch (op) {
case WMAP_MAP: ptail = list_collect(ptail, item); break;
@@ -10819,11 +10828,11 @@ val rot(val seq, val n_in)
return seq;
}
-val find(val item, val seq, val testfun, val keyfun)
+val find(val item, val seq, val testfun_in, val keyfun_in)
{
val self = lit("find");
- testfun = default_arg(testfun, equal_f);
- keyfun = default_arg(keyfun, identity_f);
+ val testfun = default_arg(testfun_in, equal_f);
+ val keyfun = default_arg(keyfun_in, identity_f);
seq_info_t si = seq_info(seq);
switch (si.kind) {
@@ -10877,11 +10886,11 @@ val find(val item, val seq, val testfun, val keyfun)
}
}
-val rfind(val item, val seq, val testfun, val keyfun)
+val rfind(val item, val seq, val testfun_in, val keyfun_in)
{
val self = lit("rfind");
- testfun = default_arg(testfun, equal_f);
- keyfun = default_arg(keyfun, identity_f);
+ val testfun = default_arg(testfun_in, equal_f);
+ val keyfun = default_arg(keyfun_in, identity_f);
seq_info_t si = seq_info(seq);
switch (si.kind) {
@@ -11199,11 +11208,11 @@ val rfind_if(val predi, val seq, val key)
return found;
}
-val pos(val item, val seq, val testfun, val keyfun)
+val pos(val item, val seq, val testfun_in, val keyfun_in)
{
val self = lit("pos");
- testfun = default_arg(testfun, equal_f);
- keyfun = default_arg(keyfun, identity_f);
+ val testfun = default_arg(testfun_in, equal_f);
+ val keyfun = default_arg(keyfun_in, identity_f);
seq_info_t si = seq_info(seq);
switch (si.kind) {
@@ -11260,11 +11269,11 @@ val pos(val item, val seq, val testfun, val keyfun)
}
}
-val rpos(val item, val seq, val testfun, val keyfun)
+val rpos(val item, val seq, val testfun_in, val keyfun_in)
{
val self = lit("rpos");
- testfun = default_arg(testfun, equal_f);
- keyfun = default_arg(keyfun, identity_f);
+ val testfun = default_arg(testfun_in, equal_f);
+ val keyfun = default_arg(keyfun_in, identity_f);
seq_info_t si = seq_info(seq);
switch (si.kind) {
@@ -11525,12 +11534,13 @@ val subst(val oldv, val newv, val seq, val testfun_in, val keyfun_in)
{
val self = lit("subst");
seq_iter_t iter;
- seq_iter_init(self, &iter, seq);
val elem;
val testfun = default_arg(testfun_in, equal_f);
val keyfun = default_arg(keyfun_in, identity_f);
list_collect_decl (out, ptail);
+ seq_iter_init(self, &iter, seq);
+
while (seq_get(&iter, &elem)) {
val key = funcall1(keyfun, elem);
ptail = list_collect(ptail, if3(funcall2(testfun, oldv, key), newv, elem));
@@ -12003,7 +12013,7 @@ val drop_until(val pred, val seq, val keyfun)
}
}
-val in(val seq, val item, val testfun, val keyfun)
+val in(val seq, val item, val testfun_in, val keyfun_in)
{
val self = lit("in");
seq_info_t si = seq_info(seq);
@@ -12015,8 +12025,8 @@ val in(val seq, val item, val testfun, val keyfun)
case STR:
case LSTR:
{
- testfun = default_arg(testfun, equal_f);
- keyfun = default_arg(keyfun, identity_f);
+ val testfun = default_arg(testfun_in, equal_f);
+ val keyfun = default_arg(keyfun_in, identity_f);
val len = length_str(seq);
val ind;
@@ -12032,8 +12042,8 @@ val in(val seq, val item, val testfun, val keyfun)
}
case VEC:
{
- testfun = default_arg(testfun, equal_f);
- keyfun = default_arg(keyfun, identity_f);
+ val testfun = default_arg(testfun_in, equal_f);
+ val keyfun = default_arg(keyfun_in, identity_f);
val len = length_vec(seq);
val ind;
@@ -12050,7 +12060,7 @@ val in(val seq, val item, val testfun, val keyfun)
default:
switch (si.kind) {
case SEQ_HASHLIKE:
- if (null_or_missing_p(testfun) && null_or_missing_p(keyfun))
+ if (null_or_missing_p(testfun_in) && null_or_missing_p(keyfun_in))
return tnil(gethash_e(self, si.obj, item));
/* fallthrough */
case SEQ_LISTLIKE:
@@ -12058,12 +12068,11 @@ val in(val seq, val item, val testfun, val keyfun)
{
seq_iter_t iter;
val elem;
+ val testfun = default_arg(testfun_in, equal_f);
+ val keyfun = default_arg(keyfun_in, identity_f);
seq_iter_init(self, &iter, seq);
- testfun = default_arg(testfun, equal_f);
- keyfun = default_arg(keyfun, identity_f);
-
while (seq_get(&iter, &elem)) {
val key = funcall1(keyfun, elem);
if (funcall2(testfun, item, key))
@@ -12629,10 +12638,10 @@ val update(val seq, val fun)
}
static val search_common(val self, int from_right,
- val seq, val key, val testfun, val keyfun)
+ val seq, val key, val testfun_in, val keyfun_in)
{
- testfun = default_arg(testfun, equal_f);
- keyfun = default_arg(keyfun, identity_f);
+ val testfun = default_arg(testfun_in, equal_f);
+ val keyfun = default_arg(keyfun_in, identity_f);
seq_iter_t si, ki;
seq_iter_init(self, &si, seq);
diff --git a/linenoise/linenoise.c b/linenoise/linenoise.c
index ec88f378..d3d6640b 100644
--- a/linenoise/linenoise.c
+++ b/linenoise/linenoise.c
@@ -2008,8 +2008,9 @@ static void edit_in_editor(lino_t *l) {
if (fo) {
char cmd[256];
- snprintf(cmd, sizeof cmd, "%s %s", ed, path);
int preserve = 0;
+
+ snprintf(cmd, sizeof cmd, "%s %s", ed, path);
tr(l->data, '\r', '\n');
if (lino_os.puts_file_fn(fo, l->data) && lino_os.puts_file_fn(fo, L"\n"))
diff --git a/parser.c b/parser.c
index bca07741..c30020fc 100644
--- a/parser.c
+++ b/parser.c
@@ -1232,12 +1232,13 @@ static int is_balanced_line(const wchar_t *line, void *ctx)
};
int count[32], sp = 0;
enum state state[32];
- count[sp] = 0;
- state[sp] = ST_START;
wchar_t ch;
(void) ctx;
+ count[sp] = 0;
+ state[sp] = ST_START;
+
while ((ch = *line++) != 0) {
again:
if (sp >= 30)
diff --git a/regex.c b/regex.c
index 7cf22f45..9ebefe20 100644
--- a/regex.c
+++ b/regex.c
@@ -1104,8 +1104,8 @@ static void nfa_map_states(nfa_state_t *s,
static void nfa_count_one(nfa_state_t *s, mem_t *ctx)
{
- (void) s;
int *pcount = coerce(int *, ctx);
+ (void) s;
(*pcount)++;
}
@@ -2346,10 +2346,10 @@ static void print_rec(val exp, val stream, int *semi_flag)
val args = rest(exp);
if (sym == set_s || sym == cset_s) {
- putc_clear_flag(chr('['), stream, semi_flag);
-
val first_p = t;
+ putc_clear_flag(chr('['), stream, semi_flag);
+
if (sym == cset_s) {
put_char(chr('^'), stream);
first_p = nil;
diff --git a/signal.c b/signal.c
index 3c7dca10..2287ae2c 100644
--- a/signal.c
+++ b/signal.c
@@ -370,8 +370,8 @@ int sig_mask(int how, const small_sigset_t *set, small_sigset_t *oldset)
if (sig_blocked_cache.set != pnew->set) {
static sigset_t blank;
sigset_t real_newset = blank, real_oldset;
- sig_blocked_cache = *pnew;
int ret;
+ sig_blocked_cache = *pnew;
#if HAVE_VALGRIND
VALGRIND_MAKE_MEM_DEFINED(&real_oldset, sizeof real_oldset);
#endif
diff --git a/stream.c b/stream.c
index 34609f87..ebbb7e19 100644
--- a/stream.c
+++ b/stream.c
@@ -4173,11 +4173,11 @@ struct strm_ctx *get_ctx(val stream)
return s->ctx;
}
-val get_string(val stream_in, val nchars, val close_after_p)
+val get_string(val stream_in, val nchars_in, val close_after_p)
{
val stream = default_arg_strict(stream_in, std_input);
val strstream = make_string_output_stream();
- nchars = default_null_arg(nchars);
+ val nchars = default_null_arg(nchars_in);
val ch;
if (nchars) {
diff --git a/struct.c b/struct.c
index fccd0928..f2fb78a5 100644
--- a/struct.c
+++ b/struct.c
@@ -1167,9 +1167,9 @@ static struct stslot *lookup_static_slot_desc(struct struct_type *st, val sym)
}
}
} else {
- slot_cache = coerce(slot_cache_set_t *,
- chk_calloc(SLOT_CACHE_SIZE,
- sizeof (slot_cache_set_t)));
+ slot_cache_set_t *slot_cache = coerce(slot_cache_set_t *,
+ chk_calloc(SLOT_CACHE_SIZE,
+ sizeof *slot_cache));
slot_cache_set_t *set = &slot_cache[id % SLOT_CACHE_SIZE];
val key = cons(sym, num_fast(id));
val sl = gethash(slot_hash, key);
@@ -1734,14 +1734,13 @@ static val umethod_args_fun(val dargs, struct args *args)
cnum da_nargs = da->fill + c_num(length(da->list), self);
cnum index = 0;
val strct = args_get(args, &index);
+ struct struct_inst *si = struct_handle_for_slot(strct, self, sym);
args_decl(args_call, max(args->fill + da_nargs, ARGS_MIN));
args_add(args_call, strct);
args_cat(args_call, da);
args_normalize_exact(args_call, da_nargs + 1);
args_cat_zap_from(args_call, args, index);
- struct struct_inst *si = struct_handle_for_slot(strct, self, sym);
-
if (sym && symbolp(sym)) {
loc ptr = lookup_slot(strct, si, sym);
if (!nullocp(ptr))
@@ -2035,10 +2034,13 @@ val static_slot_type_reg(val slot, val strct)
val get_special_slot(val obj, enum special_slot spidx)
{
val slot = *special_sym[spidx];
- if (opt_compat && opt_compat <= 224)
+
+ if (opt_compat && opt_compat <= 224) {
return maybe_slot(obj, slot);
- struct struct_inst *si = coerce(struct struct_inst *, obj->co.handle);
- return get_special_static_slot(si->type, spidx, slot);
+ } else {
+ struct struct_inst *si = coerce(struct struct_inst *, obj->co.handle);
+ return get_special_static_slot(si->type, spidx, slot);
+ }
}
val get_special_required_slot(val obj, enum special_slot spidx)
diff --git a/sysif.c b/sysif.c
index 13f5f2a6..3cdf14d2 100644
--- a/sysif.c
+++ b/sysif.c
@@ -271,10 +271,12 @@ val usleep_wrap(val usec)
sig_save_enable;
#if HAVE_POSIX_NANOSLEEP
- struct timespec ts;
- ts.tv_sec = u / 1000000;
- ts.tv_nsec = (u % 1000000) * 1000;
- retval = if3(nanosleep(&ts, 0) == 0, t, nil);
+ {
+ struct timespec ts;
+ ts.tv_sec = u / 1000000;
+ ts.tv_nsec = (u % 1000000) * 1000;
+ retval = if3(nanosleep(&ts, 0) == 0, t, nil);
+ }
#elif HAVE_POSIX_SLEEP && HAVE_POSIX_USLEEP
retval = if2(sleep(u / 1000000) == 0 &&
usleep(u % 1000000) == 0, t);
@@ -2525,13 +2527,17 @@ val setrlimit_wrap(val resource, val rlim)
{
val self = lit("setrlimit");
struct rlimit rl;
+
rl.rlim_cur = c_unum(slot(rlim, cur_s), self);
rl.rlim_max = c_unum(slot(rlim, max_s), self);
- int res = setrlimit(c_int(resource, self), &rl);
- if (res != 0)
- uw_ethrowf(system_error_s, lit("~a failed for ~a: ~d/~s"),
- self, resource, num(errno), errno_to_str(errno), nao);
+ {
+ int res = setrlimit(c_int(resource, self), &rl);
+
+ if (res != 0)
+ uw_ethrowf(system_error_s, lit("~a failed for ~a: ~d/~s"),
+ self, resource, num(errno), errno_to_str(errno), nao);
+ }
return t;
}
diff --git a/time.c b/time.c
index 43dd7cb1..18919f1f 100644
--- a/time.c
+++ b/time.c
@@ -407,10 +407,11 @@ static val time_string_meth(val time_struct, val format)
{
val self = lit("(meth time-string)");
struct tm tms = all_zero_init;
- time_struct_to_tm(&tms, time_struct, t, self);
char buffer[512] = "";
char *fmt = utf8_dup_to(c_str(format, self));
+ time_struct_to_tm(&tms, time_struct, t, self);
+
if (strftime(buffer, sizeof buffer, fmt, &tms) == 0)
buffer[0] = 0;
@@ -425,9 +426,10 @@ static val time_parse_meth(val time_struct, val format, val string)
{
val self = lit("(meth time-parse)");
struct tm tms = all_zero_init;
- time_struct_to_tm(&tms, time_struct, nil, self);
val ret = nil;
+ time_struct_to_tm(&tms, time_struct, nil, self);
+
{
const wchar_t *w_str = c_str(string, self);
const wchar_t *w_fmt = c_str(format, self);
diff --git a/tree.c b/tree.c
index 8b3230e3..0c803d8e 100644
--- a/tree.c
+++ b/tree.c
@@ -537,28 +537,30 @@ static val tr_do_delete_specific(val tree, struct tree *tr, val subtree,
return subtree;
}
- val tr_key = if3(tr->key_fn,
- funcall1(tr->key_fn, subtree->tn.key),
- subtree->tn.key);
-
- if (if3(tr->less_fn,
- funcall2(tr->less_fn, key, tr_key),
- less(key, tr_key)))
{
- val le = subtree->tn.left;
- return tr_do_delete_specific(tree, tr, le, subtree, key, thisnode);
- } else if (if3(tr->equal_fn == nil,
- equal(key, tr_key),
- funcall2(tr->equal_fn, key, tr_key)))
- {
- uses_or2;
- val le = subtree->tn.left;
- val ri = subtree->tn.right;
- return or2(tr_do_delete_specific(tree, tr, le, subtree, key, thisnode),
- tr_do_delete_specific(tree, tr, ri, subtree, key, thisnode));
- } else {
- val ri = subtree->tn.right;
- return tr_do_delete_specific(tree, tr, ri, subtree, key, thisnode);
+ val tr_key = if3(tr->key_fn,
+ funcall1(tr->key_fn, subtree->tn.key),
+ subtree->tn.key);
+
+ if (if3(tr->less_fn,
+ funcall2(tr->less_fn, key, tr_key),
+ less(key, tr_key)))
+ {
+ val le = subtree->tn.left;
+ return tr_do_delete_specific(tree, tr, le, subtree, key, thisnode);
+ } else if (if3(tr->equal_fn == nil,
+ equal(key, tr_key),
+ funcall2(tr->equal_fn, key, tr_key)))
+ {
+ uses_or2;
+ val le = subtree->tn.left;
+ val ri = subtree->tn.right;
+ return or2(tr_do_delete_specific(tree, tr, le, subtree, key, thisnode),
+ tr_do_delete_specific(tree, tr, ri, subtree, key, thisnode));
+ } else {
+ val ri = subtree->tn.right;
+ return tr_do_delete_specific(tree, tr, ri, subtree, key, thisnode);
+ }
}
}
diff --git a/unwind.c b/unwind.c
index efc321ef..399c3e3a 100644
--- a/unwind.c
+++ b/unwind.c
@@ -1072,6 +1072,7 @@ static val revive_cont(val dc, val arg)
mem_t *ptr;
uw_frame_t *new_uw_stack = coerce(uw_frame_t *, space + UW_CONT_FRAME_BEFORE), *fr;
int env_set = 0;
+ val result = nil;
memcpy(space, cont->stack, cont->size);
@@ -1101,7 +1102,7 @@ static val revive_cont(val dc, val arg)
#endif
}
- uw_block_begin (cont->tag, result);
+ uw_block_beg (cont->tag, result);
for (fr = new_uw_stack; ; fr = fr->uw.up) {
if (!env_set && fr->uw.type == UW_MENV) {
diff --git a/unwind.h b/unwind.h
index 3a881641..ffa52eb6 100644
--- a/unwind.h
+++ b/unwind.h
@@ -398,6 +398,16 @@ NORETURN void invalid_op(val self, val obj);
return VAL; \
} while (0)
+#define uw_block_beg(TAG, RESULTVAR) \
+ do { \
+ uw_frame_t uw_blk; \
+ obj_t **uw_rslt = &RESULTVAR; \
+ uw_push_block(&uw_blk, TAG); \
+ if (extended_setjmp(uw_blk.bl.jb)) { \
+ RESULTVAR = uw_blk.bl.result; \
+ } else { \
+ enum { dummy ## __LINE__ }
+
#define uw_block_begin(TAG, RESULTVAR) \
obj_t *RESULTVAR = nil; \
do { \
@@ -407,7 +417,7 @@ NORETURN void invalid_op(val self, val obj);
if (extended_setjmp(uw_blk.bl.jb)) { \
RESULTVAR = uw_blk.bl.result; \
} else { \
- do { } while (0)
+ enum { dummy ## __LINE__ }
#define uw_block_end \
} \
@@ -417,9 +427,12 @@ NORETURN void invalid_op(val self, val obj);
#define uw_match_env_begin \
do { \
uw_frame_t uw_env; \
- uw_push_match_env(&uw_env)
+ uw_push_match_env(&uw_env); \
+ { \
+ enum { dummy ## __LINE__ }
#define uw_match_env_end \
+ } \
uw_pop_frame(&uw_env); \
} while (0)
diff --git a/vm.c b/vm.c
index 399bef19..9aa0b72b 100644
--- a/vm.c
+++ b/vm.c
@@ -1142,18 +1142,20 @@ val vm_execute_closure(val fun, struct args *args)
}
while (fixparam >= 2) {
- fixparam -= 2;
- argw = vm.code[vm.ip++];
- unsigned xreg = vm_arg_operand_lo(argw);
- unsigned yreg = vm_arg_operand_hi(argw);
+ vm_word_t aw = vm.code[vm.ip++];
+ unsigned xreg = vm_arg_operand_lo(aw);
+ unsigned yreg = vm_arg_operand_hi(aw);
vm_set(dspl, xreg, args_get(args, &ix));
vm_set(dspl, yreg, args_get(args, &ix));
+ fixparam -= 2;
+ argw = aw;
}
if (fixparam) {
- argw = vm.code[vm.ip++];
- unsigned xreg = vm_arg_operand_lo(argw);
+ vm_word_t aw = vm.code[vm.ip++];
+ unsigned xreg = vm_arg_operand_lo(aw);
vm_set(dspl, xreg, args_get(args, &ix));
+ argw = aw;
}
if (variadic) {