diff options
author | Kaz Kylheku <kaz@kylheku.com> | 2015-12-14 20:03:39 -0800 |
---|---|---|
committer | Kaz Kylheku <kaz@kylheku.com> | 2015-12-14 20:03:39 -0800 |
commit | d4e6090d6f5d38e2901686d3b37c19da3ce7d6fa (patch) | |
tree | bcbc5e2756c7cb4a2eed018d9bc16cd2a4aa7345 /eval.c | |
parent | a1dbd3f219a2ad552de98d5e9e7b28af975ab47d (diff) | |
download | txr-d4e6090d6f5d38e2901686d3b37c19da3ce7d6fa.tar.gz txr-d4e6090d6f5d38e2901686d3b37c19da3ce7d6fa.tar.bz2 txr-d4e6090d6f5d38e2901686d3b37c19da3ce7d6fa.zip |
Allow :whole and :form to do destructuring.
* eval.c (bind_macro_params): Remove the restriction that the
:whole and :form do not allow a destructuring pattern,
requring strictly a symbol. Common Lisp's &whole also
does destructuring. As a side effect of this change, the :env
parameter also supports destructuring, thought this isn't
going to be meaningful since macro environments aren't lists.
Diffstat (limited to 'eval.c')
-rw-r--r-- | eval.c | 22 |
1 files changed, 15 insertions, 7 deletions
@@ -864,20 +864,28 @@ static val bind_macro_params(val env, val menv, val params, val form, if (param == whole_k || param == form_k || param == env_k) { val nparam; val next = cdr(params); + val bform = if3(param == whole_k, whole, + if3(param == form_k, + ctx_form, menv)); if (!next) eval_error(ctx_form, lit("~s: dangling ~s in param list"), car(ctx_form), param, nao); nparam = car(next); - if (!bindable(nparam)) { + + if (bindable(nparam)) { + env_vbind_special(new_env, nparam, + bform, + specials); + } else if (consp(nparam)) { + new_env = bind_macro_params(new_env, menv, + nparam, bform, + loose_p, ctx_form); + if (!new_env) + goto nil_out; + } else { err_sym = nparam; goto nbind; } - env_vbind_special(new_env, nparam, - if3(param == whole_k, - whole, - if3(param == form_k, - ctx_form, menv)), - specials); params = cdr(next); continue; } |