diff options
Diffstat (limited to 'lib/rbtree.c')
-rw-r--r-- | lib/rbtree.c | 34 |
1 files changed, 29 insertions, 5 deletions
diff --git a/lib/rbtree.c b/lib/rbtree.c index 4ba2828a67c0..d102d9d2ffaa 100644 --- a/lib/rbtree.c +++ b/lib/rbtree.c | |||
@@ -95,10 +95,14 @@ __rb_rotate_set_parents(struct rb_node *old, struct rb_node *new, | |||
95 | 95 | ||
96 | static __always_inline void | 96 | static __always_inline void |
97 | __rb_insert(struct rb_node *node, struct rb_root *root, | 97 | __rb_insert(struct rb_node *node, struct rb_root *root, |
98 | bool newleft, struct rb_node **leftmost, | ||
98 | void (*augment_rotate)(struct rb_node *old, struct rb_node *new)) | 99 | void (*augment_rotate)(struct rb_node *old, struct rb_node *new)) |
99 | { | 100 | { |
100 | struct rb_node *parent = rb_red_parent(node), *gparent, *tmp; | 101 | struct rb_node *parent = rb_red_parent(node), *gparent, *tmp; |
101 | 102 | ||
103 | if (newleft) | ||
104 | *leftmost = node; | ||
105 | |||
102 | while (true) { | 106 | while (true) { |
103 | /* | 107 | /* |
104 | * Loop invariant: node is red | 108 | * Loop invariant: node is red |
@@ -434,19 +438,38 @@ static const struct rb_augment_callbacks dummy_callbacks = { | |||
434 | 438 | ||
435 | void rb_insert_color(struct rb_node *node, struct rb_root *root) | 439 | void rb_insert_color(struct rb_node *node, struct rb_root *root) |
436 | { | 440 | { |
437 | __rb_insert(node, root, dummy_rotate); | 441 | __rb_insert(node, root, false, NULL, dummy_rotate); |
438 | } | 442 | } |
439 | EXPORT_SYMBOL(rb_insert_color); | 443 | EXPORT_SYMBOL(rb_insert_color); |
440 | 444 | ||
441 | void rb_erase(struct rb_node *node, struct rb_root *root) | 445 | void rb_erase(struct rb_node *node, struct rb_root *root) |
442 | { | 446 | { |
443 | struct rb_node *rebalance; | 447 | struct rb_node *rebalance; |
444 | rebalance = __rb_erase_augmented(node, root, &dummy_callbacks); | 448 | rebalance = __rb_erase_augmented(node, root, |
449 | NULL, &dummy_callbacks); | ||
445 | if (rebalance) | 450 | if (rebalance) |
446 | ____rb_erase_color(rebalance, root, dummy_rotate); | 451 | ____rb_erase_color(rebalance, root, dummy_rotate); |
447 | } | 452 | } |
448 | EXPORT_SYMBOL(rb_erase); | 453 | EXPORT_SYMBOL(rb_erase); |
449 | 454 | ||
455 | void rb_insert_color_cached(struct rb_node *node, | ||
456 | struct rb_root_cached *root, bool leftmost) | ||
457 | { | ||
458 | __rb_insert(node, &root->rb_root, leftmost, | ||
459 | &root->rb_leftmost, dummy_rotate); | ||
460 | } | ||
461 | EXPORT_SYMBOL(rb_insert_color_cached); | ||
462 | |||
463 | void rb_erase_cached(struct rb_node *node, struct rb_root_cached *root) | ||
464 | { | ||
465 | struct rb_node *rebalance; | ||
466 | rebalance = __rb_erase_augmented(node, &root->rb_root, | ||
467 | &root->rb_leftmost, &dummy_callbacks); | ||
468 | if (rebalance) | ||
469 | ____rb_erase_color(rebalance, &root->rb_root, dummy_rotate); | ||
470 | } | ||
471 | EXPORT_SYMBOL(rb_erase_cached); | ||
472 | |||
450 | /* | 473 | /* |
451 | * Augmented rbtree manipulation functions. | 474 | * Augmented rbtree manipulation functions. |
452 | * | 475 | * |
@@ -455,9 +478,10 @@ EXPORT_SYMBOL(rb_erase); | |||
455 | */ | 478 | */ |
456 | 479 | ||
457 | void __rb_insert_augmented(struct rb_node *node, struct rb_root *root, | 480 | void __rb_insert_augmented(struct rb_node *node, struct rb_root *root, |
481 | bool newleft, struct rb_node **leftmost, | ||
458 | void (*augment_rotate)(struct rb_node *old, struct rb_node *new)) | 482 | void (*augment_rotate)(struct rb_node *old, struct rb_node *new)) |
459 | { | 483 | { |
460 | __rb_insert(node, root, augment_rotate); | 484 | __rb_insert(node, root, newleft, leftmost, augment_rotate); |
461 | } | 485 | } |
462 | EXPORT_SYMBOL(__rb_insert_augmented); | 486 | EXPORT_SYMBOL(__rb_insert_augmented); |
463 | 487 | ||
@@ -502,7 +526,7 @@ struct rb_node *rb_next(const struct rb_node *node) | |||
502 | * as we can. | 526 | * as we can. |
503 | */ | 527 | */ |
504 | if (node->rb_right) { | 528 | if (node->rb_right) { |
505 | node = node->rb_right; | 529 | node = node->rb_right; |
506 | while (node->rb_left) | 530 | while (node->rb_left) |
507 | node=node->rb_left; | 531 | node=node->rb_left; |
508 | return (struct rb_node *)node; | 532 | return (struct rb_node *)node; |
@@ -534,7 +558,7 @@ struct rb_node *rb_prev(const struct rb_node *node) | |||
534 | * as we can. | 558 | * as we can. |
535 | */ | 559 | */ |
536 | if (node->rb_left) { | 560 | if (node->rb_left) { |
537 | node = node->rb_left; | 561 | node = node->rb_left; |
538 | while (node->rb_right) | 562 | while (node->rb_right) |
539 | node=node->rb_right; | 563 | node=node->rb_right; |
540 | return (struct rb_node *)node; | 564 | return (struct rb_node *)node; |