summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--ChangeLog44
-rw-r--r--eval.c28
-rw-r--r--lib.c231
-rw-r--r--lib.h32
-rw-r--r--match.c34
-rw-r--r--parser.y4
-rw-r--r--regex.c17
-rw-r--r--txr.c2
8 files changed, 252 insertions, 140 deletions
diff --git a/ChangeLog b/ChangeLog
index 8b134c00..a01223a0 100644
--- a/ChangeLog
+++ b/ChangeLog
@@ -1,6 +1,48 @@
2014-01-22 Kaz Kylheku <kaz@kylheku.com>
- Support function versions of if, and, or so that partial
+ Changes to the list collection mechanism to improve
+ the extension of list operations over vectors and strings.
+
+ * eval.c (do_eval_args, bindings_helper, op_each,
+ subst_vars, supplement_op_syms, mapcarv, mappendv): Switch from
+ list_collect_* macros to functions.
+
+ * lib.c (copy_list): Switch from list_collect* macros to functions.
+ Use list_collect_nconc for the final terminator. Doing a copy
+ there with list_collect_append was actually wasteful, and now
+ that list_collect_append calls copy_list in places, it triggered
+ runaway recursion.
+ (make_like): Bugfix: list_vector was used instead of vector_list.
+ (to_seq, list_collect, list_collect_nconc, list_collect_append): New
+ functions.
+ (append2, appendv, nappend2, sub_list, replace_list, ldiff, remq,
+ remql, remqual, remove_if, keep_if, proper_plist_to_alist,
+ improper_plist_to_alist, split_str, split_str_set, tok_str,
+ list_str, chain, andf, orf, lis_vector, mapcar, mapcon, mappend,
+ merge, set_diff, env): Switch from list_collect* macros to functions.
+ (replace_str, replace_vec): Allow single item replacement sequence.
+
+ * lib.h (to_seq): Declared.
+ (list_collect, list_collect_nconc, list_collect_append): Macros
+ removed, replaced by function declarations of the same name.
+ These functions return the new ptail since they cannot assign
+ to it, requiring all uses to be updated to do the assignment
+ of the returned value.
+ (list_collect_decl): Use val rather than obj_t *.
+
+ * match.c (vars_to_bindings, h_coll, subst_vars, extract_vars,
+ extract_bindings, do_output_line, do_output, v_gather, v_collect):
+ Switch from list_collect* macros to functions.
+
+ * parser.y (o_elems_transform): Likewise.
+
+ * regex.c (dv_compile_regex, regsub): Likewise.
+
+ * txr.c (txr_main): Likewise.
+
+2014-01-22 Kaz Kylheku <kaz@kylheku.com>
+
+ Support function versions of if, and, or so that partial
evaluation like (op or @1 42) or (op if (eq @1 foo) bar xyzzy)
is possible.
diff --git a/eval.c b/eval.c
index 85233904..5ea361d8 100644
--- a/eval.c
+++ b/eval.c
@@ -414,9 +414,9 @@ static val do_eval_args(val form, val env, val ctx_form,
{
list_collect_decl (values, ptail);
for (; consp(form); form = cdr(form))
- list_collect(ptail, do_eval(car(form), env, ctx_form, lookup));
+ ptail = list_collect(ptail, do_eval(car(form), env, ctx_form, lookup));
if (form)
- list_collect_append(ptail, do_eval(form, env, ctx_form, lookup));
+ ptail = list_collect_append(ptail, do_eval(form, env, ctx_form, lookup));
return values;
}
@@ -582,7 +582,7 @@ static val bindings_helper(val vars, val env, val sequential, val ctx_form)
car(ctx_form), var, nao);
}
- list_collect (ptail, cons(var, val));
+ ptail = list_collect (ptail, cons(var, val));
if (sequential)
env_replace_vbind(nenv, new_bindings);
@@ -645,9 +645,9 @@ static val op_each(val form, val env)
{
val res = eval_progn(body, make_env(new_bindings, nil, env), form);
if (collect)
- list_collect(ptail, res);
+ ptail = list_collect(ptail, res);
else if (append)
- list_collect_nconc(ptail, res);
+ ptail = list_collect_nconc(ptail, res);
}
}
@@ -1291,7 +1291,7 @@ static val subst_vars(val forms, val env)
continue;
} else if (sym == quasi_s) {
val nested = subst_vars(rest(form), env);
- list_collect_append(iter, nested);
+ iter = list_collect_append(iter, nested);
forms = cdr(forms);
continue;
} else if (sym == expr_s) {
@@ -1300,7 +1300,7 @@ static val subst_vars(val forms, val env)
continue;
} else {
val nested = subst_vars(form, env);
- list_collect_append(iter, nested);
+ iter = list_collect_append(iter, nested);
forms = cdr(forms);
continue;
}
@@ -1320,7 +1320,7 @@ static val subst_vars(val forms, val env)
form, nao);
}
- list_collect(iter, form);
+ iter = list_collect(iter, form);
forms = cdr(forms);
}
@@ -1604,8 +1604,8 @@ static val supplement_op_syms(val ssyms, val max)
val num = car(entry);
for (; lt(ni, num); ni = plus(ni, one))
- list_collect(tl, cons(ni, gensym(format_op_arg(ni))));
- list_collect(tl, entry);
+ tl = list_collect(tl, cons(ni, gensym(format_op_arg(ni))));
+ tl = list_collect(tl, entry);
}
return outsyms;
@@ -1838,11 +1838,11 @@ val mapcarv(val fun, val list_of_lists)
val list = car(iter);
if (!list)
return make_like(out, list_orig);
- list_collect(atail, car(list));
+ atail = list_collect(atail, car(list));
*car_l(iter) = cdr(list);
}
- list_collect(otail, apply(fun, args, nil));
+ otail = list_collect(otail, apply(fun, args, nil));
}
}
}
@@ -1864,11 +1864,11 @@ static val mappendv(val fun, val list_of_lists)
val list = car(iter);
if (!list)
return make_like(out, list_orig);
- list_collect(atail, car(list));
+ atail = list_collect(atail, car(list));
*car_l(iter) = cdr(list);
}
- list_collect_append (otail, apply(fun, args, nil));
+ otail = list_collect_append(otail, apply(fun, args, nil));
}
}
}
diff --git a/lib.c b/lib.c
index be9e030b..7da379b6 100644
--- a/lib.c
+++ b/lib.c
@@ -389,17 +389,16 @@ val push(val value, val *plist)
/* Unsafe for mutating object fields: use mpush macro. */
return *plist = cons(value, *plist);
}
-
val copy_list(val list)
{
list_collect_decl (out, ptail);
while (consp(list)) {
- list_collect(ptail, car(list));
+ ptail = list_collect(ptail, car(list));
list = cdr(list);
}
- list_collect_append(ptail, list);
+ ptail = list_collect_nconc(ptail, list);
return out;
}
@@ -409,7 +408,7 @@ val make_like(val list, val thatobj)
if (list != thatobj) {
switch (type(thatobj)) {
case VEC:
- return list_vector(list);
+ return vector_list(list);
case STR:
case LIT:
case LSTR:
@@ -425,6 +424,97 @@ val make_like(val list, val thatobj)
return list;
}
+val to_seq(val seq)
+{
+ switch (type(seq)) {
+ case VEC:
+ case STR:
+ case LIT:
+ case LSTR:
+ case NIL:
+ case CONS:
+ case LCONS:
+ return seq;
+ default:
+ return cons(seq, nil);
+ }
+}
+
+val *list_collect(val *ptail, val obj)
+{
+ switch (type(*ptail)) {
+ case NIL:
+ set(*ptail, cons(obj, nil));
+ return ptail;
+ case CONS:
+ case LCONS:
+ ptail = tail(*ptail);
+ set(*ptail, cons(obj, nil));
+ return ptail;
+ case VEC:
+ replace_vec(*ptail, cons(obj, nil), t, t);
+ return ptail;
+ case STR:
+ case LIT:
+ case LSTR:
+ replace_str(*ptail, cons(obj, nil), t, t);
+ return ptail;
+ default:
+ uw_throwf(error_s, lit("cannot append ~s to ~s"), obj, *ptail, nao);
+ }
+}
+
+val *list_collect_nconc(val *ptail, val obj)
+{
+ switch (type(*ptail)) {
+ case NIL:
+ set(*ptail, obj);
+ return ptail;
+ case CONS:
+ case LCONS:
+ ptail = tail(*ptail);
+ set(*ptail, obj);
+ return ptail;
+ case VEC:
+ replace_vec(*ptail, obj, t, t);
+ return ptail;
+ case STR:
+ case LIT:
+ case LSTR:
+ replace_str(*ptail, obj, t, t);
+ return ptail;
+ default:
+ uw_throwf(error_s, lit("cannot nconc ~s to ~s"), obj, *ptail, nao);
+ }
+}
+
+val *list_collect_append(val *ptail, val obj)
+{
+ switch (type(*ptail)) {
+ case NIL:
+ set(*ptail, obj);
+ return ptail;
+ case CONS:
+ case LCONS:
+ set(*ptail, copy_list(*ptail));
+ ptail = tail(*ptail);
+ set(*ptail, obj);
+ return ptail;
+ case VEC:
+ set(*ptail, copy_vec(*ptail));
+ replace_vec(*ptail, obj, t, t);
+ return ptail;
+ case STR:
+ case LIT:
+ case LSTR:
+ set(*ptail, copy_str(*ptail));
+ replace_str(*ptail, obj, t, t);
+ return ptail;
+ default:
+ uw_throwf(error_s, lit("cannot append ~s to ~s"), obj, *ptail, nao);
+ }
+}
+
val nreverse(val in)
{
val rev = nil;
@@ -456,8 +546,8 @@ val append2(val list1, val list2)
{
list_collect_decl (out, ptail);
- list_collect_append (ptail, list1);
- list_collect_append (ptail, list2);
+ ptail = list_collect_append (ptail, list1);
+ ptail = list_collect_append (ptail, list2);
return out;
}
@@ -468,9 +558,7 @@ val appendv(val lists)
for (; lists; lists = cdr(lists)) {
val item = car(lists);
- if (!listp(*ptail))
- uw_throwf(error_s, lit("append: ~s is not a list"), *ptail, nao);
- list_collect_append(ptail, item);
+ ptail = list_collect_append(ptail, item);
}
return out;
@@ -480,8 +568,8 @@ val nappend2(val list1, val list2)
{
list_collect_decl (out, ptail);
- list_collect_nconc (ptail, list1);
- list_collect_nconc (ptail, list2);
+ ptail = list_collect_nconc (ptail, list1);
+ ptail = list_collect_nconc (ptail, list2);
return out;
}
@@ -526,7 +614,7 @@ val sub_list(val list, val from, val to)
if (ge(i, to))
break;
if (from && ge(i, from))
- list_collect(ptail, car(iter));
+ ptail = list_collect(ptail, car(iter));
}
return out;
@@ -572,10 +660,11 @@ val replace_list(val list, val items, val from, val to)
for (i = zero, iter = list; iter; iter = cdr(iter), i = plus(i, one)) {
if (from && ge(i, from))
break;
- list_collect (ptail, car(iter));
+ ptail = list_collect(ptail, car(iter));
}
- list_collect_nconc(ptail, listp(items) ? items : list_vector(items));
+ ptail = list_collect_nconc(ptail, if3(listp(items),
+ items, list_vector(items)));
return out;
}
} else {
@@ -586,11 +675,11 @@ val replace_list(val list, val items, val from, val to)
if (ge(i, to))
break;
if (from && lt(i, from))
- list_collect(ptail, car(iter));
+ ptail = list_collect(ptail, car(iter));
}
- list_collect_nconc(ptail, append2(listp(items) ? items
- : list_vector(items),
+ ptail = list_collect_nconc(ptail, append2(if3(listp(items), items,
+ list_vector(items)),
iter));
return out;
}
@@ -656,13 +745,13 @@ val ldiff(val list1, val list2)
case LSTR:
case VEC:
while (list1 && !equal(list1, list2)) {
- list_collect (ptail, car(list1));
+ ptail = list_collect(ptail, car(list1));
list1 = cdr(list1);
}
break;
default:
while (list1 && list1 != list2) {
- list_collect (ptail, car(list1));
+ ptail = list_collect(ptail, car(list1));
list1 = cdr(list1);
}
break;
@@ -700,11 +789,11 @@ val remq(val obj, val list)
for (; list; list = cdr(list)) {
if (car(list) == obj) {
- list_collect_nconc(ptail, ldiff(cdr(lastmatch), list));
+ ptail = list_collect_nconc(ptail, ldiff(cdr(lastmatch), list));
lastmatch = list;
}
}
- list_collect_nconc(ptail, cdr(lastmatch));
+ ptail = list_collect_nconc(ptail, cdr(lastmatch));
return make_like(out, list_orig);
}
@@ -716,11 +805,11 @@ val remql(val obj, val list)
for (; list; list = cdr(list)) {
if (eql(car(list), obj)) {
- list_collect_nconc(ptail, ldiff(cdr(lastmatch), list));
+ ptail = list_collect_nconc(ptail, ldiff(cdr(lastmatch), list));
lastmatch = list;
}
}
- list_collect_nconc(ptail, cdr(lastmatch));
+ ptail = list_collect_nconc(ptail, cdr(lastmatch));
return make_like(out, list_orig);
}
@@ -732,11 +821,11 @@ val remqual(val obj, val list)
for (; list; list = cdr(list)) {
if (equal(car(list), obj)) {
- list_collect_nconc(ptail, ldiff(cdr(lastmatch), list));
+ ptail = list_collect_nconc(ptail, ldiff(cdr(lastmatch), list));
lastmatch = list;
}
}
- list_collect_nconc(ptail, cdr(lastmatch));
+ ptail = list_collect_nconc(ptail, cdr(lastmatch));
return make_like(out, list_orig);
}
@@ -754,11 +843,11 @@ val remove_if(val pred, val list, val key)
val satisfies = funcall1(pred, subj);
if (satisfies) {
- list_collect_nconc(ptail, ldiff(cdr(lastmatch), list));
+ ptail = list_collect_nconc(ptail, ldiff(cdr(lastmatch), list));
lastmatch = list;
}
}
- list_collect_nconc(ptail, cdr(lastmatch));
+ ptail = list_collect_nconc(ptail, cdr(lastmatch));
return make_like(out, list_orig);
}
@@ -776,11 +865,11 @@ val keep_if(val pred, val list, val key)
val satisfies = funcall1(pred, subj);
if (!satisfies) {
- list_collect_nconc(ptail, ldiff(cdr(lastmatch), list));
+ ptail = list_collect_nconc(ptail, ldiff(cdr(lastmatch), list));
lastmatch = list;
}
}
- list_collect_nconc(ptail, cdr(lastmatch));
+ ptail = list_collect_nconc(ptail, cdr(lastmatch));
return make_like(out, list_orig);
}
@@ -1337,7 +1426,7 @@ val proper_plist_to_alist(val list)
for (; list; list = cdr(cdr(list))) {
val ind = first(list);
val prop = second(list);
- list_collect (ptail, cons(ind, prop));
+ ptail = list_collect(ptail, cons(ind, prop));
}
return out;
@@ -1351,10 +1440,10 @@ val improper_plist_to_alist(val list, val boolean_keys)
val ind = first(list);
if (memqual(ind, boolean_keys)) {
- list_collect (ptail, cons(ind, t));
+ ptail = list_collect(ptail, cons(ind, t));
} else {
val prop = second(list);
- list_collect (ptail, cons(ind, prop));
+ ptail = list_collect(ptail, cons(ind, prop));
list = cdr(list);
}
}
@@ -1995,8 +2084,9 @@ val sub_str(val str_in, val from, val to)
val replace_str(val str_in, val items, val from, val to)
{
+ val itseq = to_seq(items);
val len = length_str(str_in);
- val len_it = length(items);
+ val len_it = length(itseq);
val len_rep;
if (type(str_in) != STR)
@@ -2045,23 +2135,23 @@ val replace_str(val str_in, val items, val from, val to)
if (zerop(len_it))
return str_in;
- if (stringp(items)) {
- wmemcpy(str_in->st.str + c_num(from), c_str(items), c_num(len_it));
+ if (stringp(itseq)) {
+ wmemcpy(str_in->st.str + c_num(from), c_str(itseq), c_num(len_it));
} else {
val iter;
cnum f = c_num(from);
cnum t = c_num(to);
cnum s;
- if (listp(items)) {
- for (iter = items; iter && f != t; iter = cdr(iter), f++)
+ if (listp(itseq)) {
+ for (iter = itseq; iter && f != t; iter = cdr(iter), f++)
str_in->st.str[f] = c_chr(car(iter));
- } else if (vectorp(items)) {
+ } else if (vectorp(itseq)) {
for (s = 0; f != t; f++, s++)
- str_in->st.str[f] = c_chr(vecref(items, num(s)));
+ str_in->st.str[f] = c_chr(vecref(itseq, num(s)));
} else {
uw_throwf(error_s, lit("replace-str: source object ~s not supported"),
- items, nao);
+ itseq, nao);
}
}
return str_in;
@@ -2132,7 +2222,7 @@ val split_str(val str, val sep)
if (eql(pos, new_pos) && len == zero)
new_pos = plus(new_pos, one);
- list_collect(iter, sub_str(str, pos, new_pos));
+ iter = list_collect(iter, sub_str(str, pos, new_pos));
pos = new_pos;
if (len) {
@@ -2162,7 +2252,7 @@ val split_str(val str, val sep)
size_t span = (psep != 0) ? psep - cstr : wcslen(cstr);
val piece = mkustring(num(span));
init_str(piece, cstr);
- list_collect(iter, piece);
+ iter = list_collect(iter, piece);
cstr += span;
if (psep != 0) {
cstr += len_sep;
@@ -2192,7 +2282,7 @@ val split_str_set(val str, val set)
size_t span = wcscspn(cstr, cset);
val piece = mkustring(num(span));
init_str(piece, cstr);
- list_collect (iter, piece);
+ iter = list_collect(iter, piece);
cstr += span;
if (*cstr) {
cstr++;
@@ -2218,16 +2308,16 @@ val tok_str(val str, val tok_regex, val keep_sep)
if (!len) {
if (keep_sep)
- list_collect(iter, sub_str(str, pos, t));
+ iter = list_collect(iter, sub_str(str, pos, t));
break;
}
end = plus(new_pos, len);
if (keep_sep)
- list_collect(iter, sub_str(str, pos, new_pos));
+ iter = list_collect(iter, sub_str(str, pos, new_pos));
- list_collect(iter, sub_str(str, new_pos, end));
+ iter = list_collect(iter, sub_str(str, new_pos, end));
pos = end;
@@ -2243,7 +2333,7 @@ val list_str(val str)
const wchar_t *cstr = c_str(str);
list_collect_decl (out, iter);
while (*cstr)
- list_collect(iter, chr(*cstr++));
+ iter = list_collect(iter, chr(*cstr++));
return out;
}
@@ -3526,10 +3616,10 @@ val chain(val first_fun, ...)
if (first_fun != nao) {
val next_fun;
va_start (vl, first_fun);
- list_collect (iter, first_fun);
+ iter = list_collect(iter, first_fun);
while ((next_fun = va_arg(vl, val)) != nao)
- list_collect (iter, next_fun);
+ iter = list_collect(iter, next_fun);
va_end (vl);
}
@@ -3559,10 +3649,10 @@ val andf(val first_fun, ...)
if (first_fun != nao) {
val next_fun;
va_start (vl, first_fun);
- list_collect (iter, first_fun);
+ iter = list_collect(iter, first_fun);
while ((next_fun = va_arg(vl, val)) != nao)
- list_collect (iter, next_fun);
+ iter = list_collect(iter, next_fun);
va_end (vl);
}
@@ -3602,10 +3692,10 @@ val orf(val first_fun, ...)
if (first_fun != nao) {
val next_fun;
va_start (vl, first_fun);
- list_collect (iter, first_fun);
+ iter = list_collect(iter, first_fun);
while ((next_fun = va_arg(vl, val)) != nao)
- list_collect (iter, next_fun);
+ iter = list_collect(iter, next_fun);
va_end (vl);
}
@@ -3759,7 +3849,7 @@ val list_vector(val vec)
len = c_num(vec->v.vec[vec_length]);
for (i = 0; i < len; i++)
- list_collect(ptail, vec->v.vec[i]);
+ ptail = list_collect(ptail, vec->v.vec[i]);
return list;
}
@@ -3825,8 +3915,9 @@ val sub_vec(val vec_in, val from, val to)
val replace_vec(val vec_in, val items, val from, val to)
{
+ val it_seq = to_seq(items);
val len = length_vec(vec_in);
- val len_it = length(items);
+ val len_it = length(it_seq);
val len_rep;
if (from == nil)
@@ -3875,15 +3966,15 @@ val replace_vec(val vec_in, val items, val from, val to)
if (zerop(len_it))
return vec_in;
- if (vectorp(items)) {
- memcpy(vec_in->v.vec + c_num(from), items->v.vec,
+ if (vectorp(it_seq)) {
+ memcpy(vec_in->v.vec + c_num(from), it_seq->v.vec,
sizeof *vec_in->v.vec * c_num(len_it));
mut(vec_in);
- } else if (stringp(items)) {
+ } else if (stringp(it_seq)) {
cnum f = c_num(from);
cnum t = c_num(to);
cnum s;
- const wchar_t *str = c_str(items);
+ const wchar_t *str = c_str(it_seq);
for (s = 0; f != t; f++, s++)
vec_in->v.vec[f] = chr(str[s]);
@@ -3892,7 +3983,7 @@ val replace_vec(val vec_in, val items, val from, val to)
cnum f = c_num(from);
cnum t = c_num(to);
- for (iter = items; iter && f != t; iter = cdr(iter), f++)
+ for (iter = it_seq; iter && f != t; iter = cdr(iter), f++)
vec_in->v.vec[f] = car(iter);
mut(vec_in);
}
@@ -4350,7 +4441,7 @@ val mapcar(val fun, val list)
val list_orig = list;
for (; list; list = cdr(list))
- list_collect (iter, funcall1(fun, car(list)));
+ iter = list_collect(iter, funcall1(fun, car(list)));
return make_like(out, list_orig);
}
@@ -4361,7 +4452,7 @@ val mapcon(val fun, val list)
val list_orig = list;
for (; list; list = cdr(list))
- list_collect_nconc (iter, funcall1(fun, list));
+ iter = list_collect_nconc(iter, funcall1(fun, list));
return make_like(out, list_orig);
}
@@ -4372,7 +4463,7 @@ val mappend(val fun, val list)
val list_orig = list;
for (; list; list = cdr(list))
- list_collect_append (iter, funcall1(fun, car(list)));
+ iter = list_collect_append(iter, funcall1(fun, car(list)));
return make_like(out, list_orig);
}
@@ -4388,20 +4479,20 @@ val merge(val list1, val list2, val lessfun, val keyfun)
if (funcall2(lessfun, el1, el2)) {
val next = cdr(list1);
*cdr_l(list1) = nil;
- list_collect_nconc(ptail, list1);
+ ptail = list_collect_nconc(ptail, list1);
list1 = next;
} else {
val next = cdr(list2);
*cdr_l(list2) = nil;
- list_collect_nconc(ptail, list2);
+ ptail = list_collect_nconc(ptail, list2);
list2 = next;
}
}
if (list1)
- list_collect_nconc(ptail, list1);
+ ptail = list_collect_nconc(ptail, list1);
else
- list_collect_nconc(ptail, list2);
+ ptail = list_collect_nconc(ptail, list2);
return out;
}
@@ -4595,7 +4686,7 @@ val set_diff(val list1, val list2, val testfun, val keyfun)
val list1_key = funcall1(keyfun, item);
if (!find(list1_key, list2, testfun, keyfun))
- list_collect (ptail, item);
+ ptail = list_collect(ptail, item);
}
}
@@ -4702,7 +4793,7 @@ val env(void)
char **iter = environ;
for (; *iter != 0; iter++)
- list_collect (ptail, string_utf8(*iter));
+ ptail = list_collect(ptail, string_utf8(*iter));
return env_list = out;
#elif HAVE_GETENVIRONMENTSTRINGS
@@ -4713,7 +4804,7 @@ val env(void)
uw_throwf(error_s, lit("out of memory"), nao);
for (; *iter; iter += wcslen(iter) + 1)
- list_collect (ptail, string(iter));
+ ptail = list_collect(ptail, string(iter));
FreeEnvironmentStringsW(env);
diff --git a/lib.h b/lib.h
index 301fe686..467866ec 100644
--- a/lib.h
+++ b/lib.h
@@ -374,6 +374,7 @@ val pop(val *plist);
val push(val v, val *plist);
val copy_list(val list);
val make_like(val list, val thatobj);
+val to_seq(val obj);
val nreverse(val in);
val reverse(val in);
val append2(val list1, val list2);
@@ -724,38 +725,16 @@ INLINE val eq(val a, val b) { return ((a) == (b) ? t : nil); }
#define c_true(c_cond) ((c_cond) ? t : nil)
#define list_collect_decl(OUT, PTAIL) \
- obj_t *OUT = nil, **PTAIL = &OUT
+ val OUT = nil, *PTAIL = &OUT
-#define list_collect(PTAIL, OBJ) \
- do { \
- if (*PTAIL) \
- PTAIL = tail(*PTAIL); \
- set(*PTAIL, cons(OBJ, nil)); \
- PTAIL = cdr_l(*PTAIL); \
- } while(0)
-
-#define list_collect_nconc(PTAIL, OBJ) \
- do { \
- if (*PTAIL) { \
- PTAIL = tail(*PTAIL); \
- } \
- set(*PTAIL, OBJ); \
- } while (0)
-
-#define list_collect_append(PTAIL, OBJ) \
- do { \
- if (*PTAIL) { \
- set(*PTAIL, copy_list(*PTAIL)); \
- PTAIL = tail(*PTAIL); \
- } \
- set(*PTAIL, OBJ); \
- } while (0)
+val *list_collect(val *pptail, val obj);
+val *list_collect_nconc(val *pptail, val obj);
+val *list_collect_append(val *pptail, val obj);
#define cons_bind(CAR, CDR, CONS) \
obj_t *c_o_n_s ## CAR ## CDR = CONS; \
obj_t *CAR = car(c_o_n_s ## CAR ## CDR); \
obj_t *CDR = cdr(c_o_n_s ## CAR ## CDR)
-
#define cons_set(CAR, CDR, CONS) \
do { \
obj_t *c_o_n_s ## CAR ## CDR = CONS; \
@@ -763,7 +742,6 @@ INLINE val eq(val a, val b) { return ((a) == (b) ? t : nil); }
CDR = cdr(c_o_n_s ## CAR ## CDR); \
} while (0)
-
#define zero num_fast(0)
#define one num_fast(1)
#define two num_fast(2)
diff --git a/match.c b/match.c
index 853926c2..143c4f12 100644
--- a/match.c
+++ b/match.c
@@ -327,10 +327,10 @@ static val vars_to_bindings(val spec, val vars, val bindings)
for (iter = vars; iter; iter = cdr(iter)) {
val item = car(iter);
if (bindable(item)) {
- list_collect (ptail, cons(item, noval_s));
+ ptail = list_collect(ptail, cons(item, noval_s));
} else if (consp(item) && bindable(first(item))) {
- list_collect (ptail, cons(first(item),
- txeval(spec, second(item), bindings)));
+ ptail = list_collect(ptail, cons(first(item),
+ txeval(spec, second(item), bindings)));
} else {
sem_error(spec, lit("not a variable spec: ~a"), item, nao);
}
@@ -795,7 +795,7 @@ static val h_coll(match_line_ctx *c)
if (!exists) {
if (dfl == noval_s)
- list_collect (ptail, var);
+ ptail = list_collect(ptail, var);
else
strictly_new_bindings = acons(var, dfl, strictly_new_bindings);
}
@@ -1381,7 +1381,7 @@ static val subst_vars(val spec, val bindings, val filter)
continue;
} else if (sym == quasi_s) {
val nested = subst_vars(rest(elem), bindings, filter);
- list_collect_append(iter, nested);
+ iter = list_collect_append(iter, nested);
spec = cdr(spec);
continue;
} else if (sym == expr_s) {
@@ -1390,13 +1390,13 @@ static val subst_vars(val spec, val bindings, val filter)
continue;
} else {
val nested = subst_vars(elem, bindings, filter);
- list_collect_append(iter, nested);
+ iter = list_collect_append(iter, nested);
spec = cdr(spec);
continue;
}
}
- list_collect(iter, elem);
+ iter = list_collect(iter, elem);
spec = cdr(spec);
}
@@ -1582,12 +1582,12 @@ static val extract_vars(val output_spec)
val sym = first(output_spec);
if (sym == var_s) {
if (bindable(second(output_spec)))
- list_collect (tai, second(output_spec));
+ tai = list_collect(tai, second(output_spec));
else
- list_collect_nconc (tai, extract_vars(second(output_spec)));
+ tai = list_collect_nconc(tai, extract_vars(second(output_spec)));
} else if (sym != expr_s) {
for (; output_spec; output_spec = cdr(output_spec))
- list_collect_nconc(tai, extract_vars(car(output_spec)));
+ tai = list_collect_nconc(tai, extract_vars(car(output_spec)));
}
}
@@ -1605,7 +1605,7 @@ static val extract_bindings(val bindings, val output_spec, val vars)
if (assoc(sym, bindings_out))
continue;
if (memq(sym, var_list))
- list_collect(ptail, binding);
+ ptail = list_collect(ptail, binding);
}
return bindings_out;
@@ -1689,7 +1689,7 @@ static void do_output_line(val bindings, val specline, val filter, val out)
val m = txeval(args, second(args), bind_a);
if (eql(mod(num_fast(i), m), n))
- list_collect_append (ptail, rest(clause));
+ ptail = list_collect_append(ptail, rest(clause));
}
if (active_mods)
@@ -1712,7 +1712,7 @@ static void do_output_line(val bindings, val specline, val filter, val out)
val m = txeval(args, second(args), bind_a);
if (eql(mod(num_fast(i), m), n))
- list_collect_append (ptail, rest(clause));
+ ptail = list_collect_append(ptail, rest(clause));
}
if (active_mods)
@@ -1812,7 +1812,7 @@ static void do_output(val bindings, val specs, val filter, val out)
val m = txeval(args, second(args), bind_a);
if (eql(mod(num_fast(i), m), n))
- list_collect_append (ptail, rest(clause));
+ ptail = list_collect_append(ptail, rest(clause));
}
if (active_mods)
@@ -1835,7 +1835,7 @@ static void do_output(val bindings, val specs, val filter, val out)
val m = txeval(args, second(args), bind_a);
if (eql(mod(num_fast(i), m), n))
- list_collect_append (ptail, rest(clause));
+ ptail = list_collect_append(ptail, rest(clause));
}
if (active_mods)
@@ -2554,7 +2554,7 @@ static val v_gather(match_files_ctx *c)
if (!success) {
*cdr_l(iter) = nil;
- list_collect_nconc(ptail, iter);
+ ptail = list_collect_nconc(ptail, iter);
} else if (success == t) {
c->bindings = new_bindings;
max_data = t;
@@ -2744,7 +2744,7 @@ static val v_collect(match_files_ctx *c)
if (!exists) {
if (dfl == noval_s)
- list_collect (ptail, var);
+ ptail = list_collect(ptail, var);
else
strictly_new_bindings = acons(var, dfl, strictly_new_bindings);
}
diff --git a/parser.y b/parser.y
index 40c231c1..37fe0814 100644
--- a/parser.y
+++ b/parser.y
@@ -1006,12 +1006,12 @@ static val o_elems_transform(val o_elems)
val pat = third(elem);
val modifiers = fourth(elem);
- list_collect(ptail, list(first(elem), sym, nil, modifiers, nao));
+ ptail = list_collect(ptail, list(first(elem), sym, nil, modifiers, nao));
elem = pat;
}
if (elem)
- list_collect(ptail, elem);
+ ptail = list_collect(ptail, elem);
}
return o_elems_out;
diff --git a/regex.c b/regex.c
index 765112ce..06e19cd2 100644
--- a/regex.c
+++ b/regex.c
@@ -1306,9 +1306,9 @@ static val dv_compile_regex(val exp)
return cobj((mem_t *) set, chset_s, &char_set_obj_ops);
} else if (sym == compound_s) {
list_collect_decl (out, iter);
- list_collect (iter, compound_s);
+ iter = list_collect(iter, compound_s);
for (; args; args = cdr(args))
- list_collect (iter, dv_compile_regex(first(args)));
+ iter = list_collect(iter, dv_compile_regex(first(args)));
return out;
} else if (sym == zeroplus_s || sym == oneplus_s ||
sym == optional_s || sym == compl_s) {
@@ -1865,16 +1865,17 @@ val regsub(val regex, val repl, val str)
if (!find) {
if (pos == zero)
return str;
- list_collect(ptail, sub_str(str, pos, nil));
+ ptail = list_collect(ptail, sub_str(str, pos, nil));
break;
}
- list_collect(ptail, sub_str(str, pos, find));
- list_collect(ptail, if3(isfunc,
- funcall1(repl, sub_str(str, find, plus(find, len))),
- repl));
+ ptail = list_collect(ptail, sub_str(str, pos, find));
+ ptail = list_collect(ptail, if3(isfunc,
+ funcall1(repl, sub_str(str, find,
+ plus(find, len))),
+ repl));
if (len == zero && eql(find, pos)) {
if (lt(pos, length_str(str))) {
- list_collect(ptail, chr_str(str, pos));
+ ptail = list_collect(ptail, chr_str(str, pos));
pos = plus(pos, one);
}
} else {
diff --git a/txr.c b/txr.c
index 452893dd..b1aca2e7 100644
--- a/txr.c
+++ b/txr.c
@@ -463,7 +463,7 @@ int txr_main(int argc, char **argv)
list_collect_decl(filenames, iter);
while (*argv)
- list_collect(iter, string_utf8(*argv++));
+ iter = list_collect(iter, string_utf8(*argv++));
retval = extract(spec, filenames, bindings);