summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorHeikki Linnakangas2016-09-04 12:02:06 +0000
committerHeikki Linnakangas2016-09-04 12:02:06 +0000
commite21db14b8a6696a2b704b89df9c4be9cd0ea8a33 (patch)
tree29168f8a80e7d7d14bec76c0cedbe8740dfd3b6a
parent6591f4226c81104f7746da6a5c00519919c560ae (diff)
Clarify the new Red-Black post-order traversal code a bit.
Coverity complained about the for(;;) loop, because it never actually iterated. It was used just to be able to use "break" to exit it early. I agree with Coverity, that's a bit confusing, so refactor the code to use if-else instead. While we're at it, use a local variable to hold the "current" node. That's shorter and clearer than referring to "iter->last_visited" all the time.
-rw-r--r--src/backend/lib/rbtree.c46
1 files changed, 24 insertions, 22 deletions
diff --git a/src/backend/lib/rbtree.c b/src/backend/lib/rbtree.c
index 242e9803cc..7fb7e55f71 100644
--- a/src/backend/lib/rbtree.c
+++ b/src/backend/lib/rbtree.c
@@ -781,27 +781,30 @@ static RBNode *
rb_inverted_iterator(RBTreeIterator *iter)
{
RBNode *came_from;
+ RBNode *current;
+
+ current = iter->last_visited;
loop:
switch ((InvertedWalkNextStep) iter->next_step)
{
/* First call, begin from root */
case NextStepBegin:
- iter->last_visited = iter->rb->root;
+ current = iter->rb->root;
iter->next_step = NextStepLeft;
goto loop;
case NextStepLeft:
- while (iter->last_visited->left != RBNIL)
- iter->last_visited = iter->last_visited->left;
+ while (current->left != RBNIL)
+ current = current->left;
iter->next_step = NextStepRight;
goto loop;
case NextStepRight:
- if (iter->last_visited->right != RBNIL)
+ if (current->right != RBNIL)
{
- iter->last_visited = iter->last_visited->right;
+ current = current->right;
iter->next_step = NextStepLeft;
goto loop;
}
@@ -810,30 +813,29 @@ loop:
break;
case NextStepUp:
- for (;;)
+ came_from = current;
+ current = current->parent;
+ if (current == NULL)
+ {
+ iter->is_over = true;
+ break; /* end of iteration */
+ }
+ else if (came_from == current->right)
+ {
+ /* return current, then continue to go up */
+ break;
+ }
+ else
{
- came_from = iter->last_visited;
- iter->last_visited = iter->last_visited->parent;
- if (iter->last_visited == NULL)
- {
- iter->is_over = true;
- break; /* end of iteration */
- }
-
- if (came_from == iter->last_visited->right)
- {
- /* return current, then continue to go up */
- break;
- }
-
/* otherwise we came from the left */
+ Assert(came_from == current->left);
iter->next_step = NextStepRight;
goto loop;
}
- break;
}
- return iter->last_visited;
+ iter->last_visited = current;
+ return current;
}
/*