* Remove the specified index from the tree. * Panics if the key is not present. */
| 711 | * Panics if the key is not present. |
| 712 | */ |
| 713 | void |
| 714 | pctrie_remove(struct pctrie *ptree, uint64_t index, pctrie_free_t freefn) |
| 715 | { |
| 716 | struct pctrie_node *node, *parent, *tmp; |
| 717 | uint64_t *m; |
| 718 | int i, slot; |
| 719 | |
| 720 | node = pctrie_root_load(ptree, NULL, PCTRIE_LOCKED); |
| 721 | if (pctrie_isleaf(node)) { |
| 722 | m = pctrie_toval(node); |
| 723 | if (*m != index) |
| 724 | panic("%s: invalid key found", __func__); |
| 725 | pctrie_root_store(ptree, NULL, PCTRIE_LOCKED); |
| 726 | return; |
| 727 | } |
| 728 | parent = NULL; |
| 729 | for (;;) { |
| 730 | if (node == NULL) |
| 731 | panic("pctrie_remove: impossible to locate the key"); |
| 732 | slot = pctrie_slot(index, node->pn_clev); |
| 733 | tmp = pctrie_node_load(&node->pn_child[slot], NULL, |
| 734 | PCTRIE_LOCKED); |
| 735 | if (pctrie_isleaf(tmp)) { |
| 736 | m = pctrie_toval(tmp); |
| 737 | if (*m != index) |
| 738 | panic("%s: invalid key found", __func__); |
| 739 | pctrie_node_store(&node->pn_child[slot], NULL, |
| 740 | PCTRIE_LOCKED); |
| 741 | node->pn_count--; |
| 742 | if (node->pn_count > 1) |
| 743 | break; |
| 744 | for (i = 0; i < PCTRIE_COUNT; i++) { |
| 745 | tmp = pctrie_node_load(&node->pn_child[i], |
| 746 | NULL, PCTRIE_LOCKED); |
| 747 | if (tmp != NULL) |
| 748 | break; |
| 749 | } |
| 750 | KASSERT(i != PCTRIE_COUNT, |
| 751 | ("%s: invalid node configuration", __func__)); |
| 752 | if (parent == NULL) |
| 753 | pctrie_root_store(ptree, tmp, PCTRIE_LOCKED); |
| 754 | else { |
| 755 | slot = pctrie_slot(index, parent->pn_clev); |
| 756 | KASSERT(pctrie_node_load( |
| 757 | &parent->pn_child[slot], NULL, |
| 758 | PCTRIE_LOCKED) == node, |
| 759 | ("%s: invalid child value", __func__)); |
| 760 | pctrie_node_store(&parent->pn_child[slot], tmp, |
| 761 | PCTRIE_LOCKED); |
| 762 | } |
| 763 | /* |
| 764 | * The child is still valid and we can not zero the |
| 765 | * pointer until all SMR references are gone. |
| 766 | */ |
| 767 | node->pn_count--; |
| 768 | pctrie_node_put(ptree, node, freefn, i); |
| 769 | break; |
| 770 | } |
no test coverage detected