203 // search for the next node |
203 // search for the next node |
204 void *next; |
204 void *next; |
205 cx_tree_iter_search_next: |
205 cx_tree_iter_search_next: |
206 // check if there is a sibling |
206 // check if there is a sibling |
207 if (iter->exiting) { |
207 if (iter->exiting) { |
208 next = iter->next; |
208 next = iter->node_next; |
209 } else { |
209 } else { |
210 next = tree_next(iter->node); |
210 next = tree_next(iter->node); |
211 iter->next = next; |
211 iter->node_next = next; |
212 } |
212 } |
213 if (next == NULL) { |
213 if (next == NULL) { |
214 // no sibling, we are done with this node and exit |
214 // no sibling, we are done with this node and exit |
215 if (iter->visit_on_exit && !iter->exiting) { |
215 if (iter->visit_on_exit && !iter->exiting) { |
216 // iter is supposed to visit the node again |
216 // iter is supposed to visit the node again |
218 } else { |
218 } else { |
219 iter->exiting = false; |
219 iter->exiting = false; |
220 if (iter->depth == 1) { |
220 if (iter->depth == 1) { |
221 // there is no parent - we have iterated the entire tree |
221 // there is no parent - we have iterated the entire tree |
222 // invalidate the iterator and free the node stack |
222 // invalidate the iterator and free the node stack |
223 iter->node = iter->next = NULL; |
223 iter->node = iter->node_next = NULL; |
224 iter->stack_capacity = iter->depth = 0; |
224 iter->stack_capacity = iter->depth = 0; |
225 free(iter->stack); |
225 free(iter->stack); |
226 iter->stack = NULL; |
226 iter->stack = NULL; |
227 } else { |
227 } else { |
228 // the parent node can be obtained from the top of stack |
228 // the parent node can be obtained from the top of stack |
270 iter.stack = malloc(sizeof(void *) * 16); |
270 iter.stack = malloc(sizeof(void *) * 16); |
271 iter.depth = 0; |
271 iter.depth = 0; |
272 |
272 |
273 // visit the root node |
273 // visit the root node |
274 iter.node = root; |
274 iter.node = root; |
275 iter.next = NULL; |
275 iter.node_next = NULL; |
276 iter.counter = 1; |
276 iter.counter = 1; |
277 iter.depth = 1; |
277 iter.depth = 1; |
278 iter.stack[0] = root; |
278 iter.stack[0] = root; |
279 iter.exiting = false; |
279 iter.exiting = false; |
280 iter.skip = false; |
280 iter.skip = false; |
281 |
281 |
282 // assign base iterator functions |
282 // assign base iterator functions |
283 iter.base.mutating = false; |
283 iter.mutating = false; |
284 iter.base.remove = false; |
284 iter.remove = false; |
285 iter.base.current_impl = NULL; |
285 iter.current_impl = NULL; |
286 iter.base.valid = cx_tree_iter_valid; |
286 iter.valid = cx_tree_iter_valid; |
287 iter.base.next = cx_tree_iter_next; |
287 iter.next = cx_tree_iter_next; |
288 iter.base.current = cx_tree_iter_current; |
288 iter.current = cx_tree_iter_current; |
289 |
289 |
290 return iter; |
290 return iter; |
291 } |
291 } |
292 |
292 |
293 static bool cx_tree_visitor_valid(void const *it) { |
293 static bool cx_tree_visitor_valid(void const *it) { |
387 iter.skip = false; |
387 iter.skip = false; |
388 iter.queue_next = NULL; |
388 iter.queue_next = NULL; |
389 iter.queue_last = NULL; |
389 iter.queue_last = NULL; |
390 |
390 |
391 // assign base iterator functions |
391 // assign base iterator functions |
392 iter.base.mutating = false; |
392 iter.mutating = false; |
393 iter.base.remove = false; |
393 iter.remove = false; |
394 iter.base.current_impl = NULL; |
394 iter.current_impl = NULL; |
395 iter.base.valid = cx_tree_visitor_valid; |
395 iter.valid = cx_tree_visitor_valid; |
396 iter.base.next = cx_tree_visitor_next; |
396 iter.next = cx_tree_visitor_next; |
397 iter.base.current = cx_tree_visitor_current; |
397 iter.current = cx_tree_visitor_current; |
398 |
398 |
399 return iter; |
399 return iter; |
400 } |
400 } |
401 |
401 |