diff --git a/extlib/benz/write.c b/extlib/benz/write.c index 33ad82f6..a7da49e6 100644 --- a/extlib/benz/write.c +++ b/extlib/benz/write.c @@ -46,57 +46,6 @@ writer_control_destroy(struct writer_control *p) kh_destroy(v, &p->visited); } -static void -traverse_shared(struct writer_control *p, pic_value obj) -{ - pic_state *pic = p->pic; - - if (p->op == OP_WRITE_SIMPLE) { - return; - } - - switch (pic_type(obj)) { - case PIC_TT_PAIR: - case PIC_TT_VECTOR: { - khash_t(l) *h = &p->labels; - khiter_t it; - int ret; - - it = kh_put(l, h, pic_ptr(obj), &ret); - if (ret != 0) { - /* first time */ - kh_val(h, it) = -1; - - if (pic_pair_p(obj)) { - /* pair */ - traverse_shared(p, pic_car(pic, obj)); - traverse_shared(p, pic_cdr(pic, obj)); - } else { - /* vector */ - size_t i; - for (i = 0; i < pic_vec_ptr(obj)->len; ++i) { - traverse_shared(p, pic_vec_ptr(obj)->data[i]); - } - } - - if (p->op == OP_WRITE) { - it = kh_get(l, h, pic_ptr(obj)); - if (kh_val(h, it) == -1) { - kh_del(l, h, it); - } - } - } else if (kh_val(h, it) == -1) { - /* second time */ - kh_val(h, it) = p->cnt++; - } - break; - } - default: - /* pass */ - break; - } -} - static void write_blob(pic_state *pic, pic_blob *blob, xFILE *file) { @@ -381,6 +330,56 @@ write_core(struct writer_control *p, pic_value obj) } } +static void +traverse(struct writer_control *p, pic_value obj) +{ + pic_state *pic = p->pic; + + if (p->op == OP_WRITE_SIMPLE) { + return; + } + + switch (pic_type(obj)) { + case PIC_TT_PAIR: + case PIC_TT_VECTOR: { + khash_t(l) *h = &p->labels; + khiter_t it; + int ret; + + it = kh_put(l, h, pic_ptr(obj), &ret); + if (ret != 0) { + /* first time */ + kh_val(h, it) = -1; + + if (pic_pair_p(obj)) { + /* pair */ + traverse(p, pic_car(pic, obj)); + traverse(p, pic_cdr(pic, obj)); + } else { + /* vector */ + size_t i; + for (i = 0; i < pic_vec_ptr(obj)->len; ++i) { + traverse(p, pic_vec_ptr(obj)->data[i]); + } + } + + if (p->op == OP_WRITE) { + it = kh_get(l, h, pic_ptr(obj)); + if (kh_val(h, it) == -1) { + kh_del(l, h, it); + } + } + } else if (kh_val(h, it) == -1) { + /* second time */ + kh_val(h, it) = p->cnt++; + } + break; + } + default: + break; + } +} + static void write(pic_state *pic, pic_value obj, xFILE *file, int mode, int op) { @@ -388,7 +387,7 @@ write(pic_state *pic, pic_value obj, xFILE *file, int mode, int op) writer_control_init(&p, pic, file, mode, op); - traverse_shared(&p, obj); + traverse(&p, obj); write_core(&p, obj);