Find an element from the table, also get the plink of the entry. The entry * is returned if the element is found, and the user should later call * `HashTableTwoPhaseUnlinkFree` with it in order to unlink and release it. Otherwise if * the key is not found, NULL is returned. These two functions should be used in pair. * `HashTableTwoPhaseUnlinkFind` pauses rehash and `HashTableTwoPhaseUnlinkFre
| 632 | * to the second one to avoid repeating the lookup |
| 633 | */ |
| 634 | dictEntry *HashTableTwoPhaseUnlinkFind(dict *d, const void *key, dictEntry ***plink, int *table_index) { |
| 635 | uint64_t h, idx, table; |
| 636 | |
| 637 | if (dictSize(d) == 0) return NULL; /* dict is empty */ |
| 638 | if (dictIsRehashing(d)) _dictRehashStep(d); |
| 639 | h = dictHashKey(d, key); |
| 640 | |
| 641 | for (table = 0; table <= 1; table++) { |
| 642 | idx = h & DICTHT_SIZE_MASK(d->ht_size_exp[table]); |
| 643 | dictEntry **ref = &d->ht_table[table][idx]; |
| 644 | while(*ref) { |
| 645 | if (key==(*ref)->key || dictCompareKeys(d, key, (*ref)->key)) { |
| 646 | *table_index = table; |
| 647 | *plink = ref; |
| 648 | dictPauseRehashing(d); |
| 649 | return *ref; |
| 650 | } |
| 651 | ref = &(*ref)->next; |
| 652 | } |
| 653 | if (!dictIsRehashing(d)) return NULL; |
| 654 | } |
| 655 | return NULL; |
| 656 | } |
| 657 | |
| 658 | void HashTableTwoPhaseUnlinkFree(dict *d, dictEntry *he, dictEntry **plink, int table_index) { |
| 659 | if (he == NULL) return; |
nothing calls this directly
no test coverage detected