diff options
author | Kaz Kylheku <kaz@kylheku.com> | 2024-06-18 03:34:35 -0700 |
---|---|---|
committer | Kaz Kylheku <kaz@kylheku.com> | 2024-06-18 03:34:35 -0700 |
commit | dd839dc6ed1abf51645f5e69572ab9e106272c33 (patch) | |
tree | 1c5187356f4b8c0f728199bf55399a025d1a118a | |
parent | 213d60b7200b7c1a1085fb239becd8e2f977b6e3 (diff) | |
download | txr-dd839dc6ed1abf51645f5e69572ab9e106272c33.tar.gz txr-dd839dc6ed1abf51645f5e69572ab9e106272c33.tar.bz2 txr-dd839dc6ed1abf51645f5e69572ab9e106272c33.zip |
bugfix: several seq_iter kinds need clone operation.
Several seq_iter_t kinds of objects cannot be correctly
bitwise copied, because they point to an iterator object
that cannot be shared.
* lib.c (seq_iter_clone_op): New static function.
(si_hash_ops, si_tree_ops, si_oop_ops, si_fast_oop_ops):
Use seq_iter_clone_op, which uses the copy function
to duplicate it->ui.iter after doing a bitwise copy of
the structure.
* lib.h (seq_iter_ops_init_full): New macro.
-rw-r--r-- | lib.c | 26 | ||||
-rw-r--r-- | lib.h | 2 |
2 files changed, 20 insertions, 8 deletions
@@ -926,6 +926,12 @@ void seq_iter_mark_op(struct seq_iter *it) gc_mark(it->ui.iter); } +static void seq_iter_clone_op(const struct seq_iter *sit, struct seq_iter *dit) +{ + *dit = *sit; + dit->ui.iter = copy(sit->ui.iter); +} + struct seq_iter_ops si_null_ops = seq_iter_ops_init_nomark(seq_iter_get_nil, seq_iter_peek_nil); @@ -935,11 +941,13 @@ struct seq_iter_ops si_list_ops = seq_iter_ops_init(seq_iter_get_list, struct seq_iter_ops si_vec_ops = seq_iter_ops_init_nomark(seq_iter_get_vec, seq_iter_peek_vec); -struct seq_iter_ops si_hash_ops = seq_iter_ops_init(seq_iter_get_hash, - seq_iter_peek_hash); +struct seq_iter_ops si_hash_ops = seq_iter_ops_init_clone(seq_iter_get_hash, + seq_iter_peek_hash, + seq_iter_clone_op); -struct seq_iter_ops si_tree_ops = seq_iter_ops_init(seq_iter_get_tree, - seq_iter_peek_tree); +struct seq_iter_ops si_tree_ops = seq_iter_ops_init_clone(seq_iter_get_tree, + seq_iter_peek_tree, + seq_iter_clone_op); struct seq_iter_ops si_range_cnum_ops = seq_iter_ops_init_nomark(seq_iter_get_range_cnum, @@ -979,14 +987,16 @@ struct seq_iter_ops si_chr_ops = seq_iter_ops_init_nomark(seq_iter_get_chr, struct seq_iter_ops si_num_ops = seq_iter_ops_init(seq_iter_get_num, seq_iter_peek_num); -struct seq_iter_ops si_oop_ops = seq_iter_ops_init_mark(seq_iter_get_oop, +struct seq_iter_ops si_oop_ops = seq_iter_ops_init_full(seq_iter_get_oop, seq_iter_peek_oop, - seq_iter_mark_oop); + seq_iter_mark_oop, + seq_iter_clone_op); struct seq_iter_ops si_fast_oop_ops = - seq_iter_ops_init_mark(seq_iter_get_fast_oop, + seq_iter_ops_init_full(seq_iter_get_fast_oop, seq_iter_peek_fast_oop, - seq_iter_mark_oop); + seq_iter_mark_oop, + seq_iter_clone_op); struct seq_iter_ops si_cat_ops = seq_iter_ops_init_mark(seq_iter_get_cat, seq_iter_peek_cat, @@ -474,6 +474,8 @@ struct seq_iter_ops { #define seq_iter_ops_init_mark(get, peek, mark) { get, peek, mark, 0 } #define seq_iter_ops_init_clone(get, peek, clone) \ { get, peek, seq_iter_mark_op, clone } +#define seq_iter_ops_init_full(get, peek, mark, clone) \ + { get, peek, mark, clone } typedef struct seq_build { val obj; |