Prehash the tombstone for cleanup
Former-commit-id: c9d97a7c7448fc769486175bea1648589487c87c
This commit is contained in:
parent
85d7a4c1e2
commit
6c83ecbb48
12
src/db.cpp
12
src/db.cpp
@ -422,7 +422,8 @@ bool redisDbPersistentData::syncDelete(robj *key)
|
|||||||
if (itr != nullptr)
|
if (itr != nullptr)
|
||||||
{
|
{
|
||||||
sds keyTombstone = sdsdup(szFromObj(key));
|
sds keyTombstone = sdsdup(szFromObj(key));
|
||||||
if (dictAdd(m_pdictTombstone, keyTombstone, nullptr) != DICT_OK)
|
uint64_t hash = dictGetHash(m_pdict, keyTombstone);
|
||||||
|
if (dictAdd(m_pdictTombstone, keyTombstone, (void*)hash) != DICT_OK)
|
||||||
sdsfree(keyTombstone);
|
sdsfree(keyTombstone);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -2290,7 +2291,7 @@ void redisDbPersistentData::initialize()
|
|||||||
{
|
{
|
||||||
m_pdbSnapshot = nullptr;
|
m_pdbSnapshot = nullptr;
|
||||||
m_pdict = dictCreate(&dbDictType,this);
|
m_pdict = dictCreate(&dbDictType,this);
|
||||||
m_pdictTombstone = dictCreate(&dbDictType,this);
|
m_pdictTombstone = dictCreate(&dbDictTypeTombstone,this);
|
||||||
m_setexpire = new(MALLOC_LOCAL) expireset();
|
m_setexpire = new(MALLOC_LOCAL) expireset();
|
||||||
m_fAllChanged = 0;
|
m_fAllChanged = 0;
|
||||||
m_fTrackingChanges = 0;
|
m_fTrackingChanges = 0;
|
||||||
@ -2477,8 +2478,11 @@ void redisDbPersistentData::ensure(const char *sdsKey, dictEntry **pde)
|
|||||||
{
|
{
|
||||||
dictAdd(m_pdict, keyNew, nullptr);
|
dictAdd(m_pdict, keyNew, nullptr);
|
||||||
}
|
}
|
||||||
*pde = dictFind(m_pdict, sdsKey);
|
uint64_t hash = dictGetHash(m_pdict, sdsKey);
|
||||||
dictAdd(m_pdictTombstone, sdsdupshared(itr.key()), nullptr);
|
dictEntry **deT;
|
||||||
|
dictht *ht;
|
||||||
|
*pde = dictFindWithPrev(m_pdict, sdsKey, hash, &deT, &ht);
|
||||||
|
dictAdd(m_pdictTombstone, sdsdupshared(itr.key()), (void*)hash);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
10
src/dict.cpp
10
src/dict.cpp
@ -326,7 +326,7 @@ int dictRehashMilliseconds(dict *d, int ms) {
|
|||||||
static void _dictRehashStep(dict *d) {
|
static void _dictRehashStep(dict *d) {
|
||||||
unsigned long iterators;
|
unsigned long iterators;
|
||||||
__atomic_load(&d->iterators, &iterators, __ATOMIC_RELAXED);
|
__atomic_load(&d->iterators, &iterators, __ATOMIC_RELAXED);
|
||||||
if (iterators == 0) dictRehash(d,1);
|
if (iterators == 0) dictRehash(d,10);
|
||||||
}
|
}
|
||||||
|
|
||||||
/* Add an element to the target hash table */
|
/* Add an element to the target hash table */
|
||||||
@ -541,14 +541,13 @@ void dictRelease(dict *d)
|
|||||||
zfree(d);
|
zfree(d);
|
||||||
}
|
}
|
||||||
|
|
||||||
dictEntry *dictFindWithPrev(dict *d, const void *key, dictEntry ***dePrevPtr, dictht **pht)
|
dictEntry *dictFindWithPrev(dict *d, const void *key, uint64_t h, dictEntry ***dePrevPtr, dictht **pht)
|
||||||
{
|
{
|
||||||
dictEntry *he;
|
dictEntry *he;
|
||||||
uint64_t h, idx, table;
|
uint64_t idx, table;
|
||||||
|
|
||||||
if (dictSize(d) == 0) return NULL; /* dict is empty */
|
if (dictSize(d) == 0) return NULL; /* dict is empty */
|
||||||
if (dictIsRehashing(d)) _dictRehashStep(d);
|
if (dictIsRehashing(d)) _dictRehashStep(d);
|
||||||
h = dictHashKey(d, key);
|
|
||||||
for (table = 0; table <= 1; table++) {
|
for (table = 0; table <= 1; table++) {
|
||||||
*pht = d->ht + table;
|
*pht = d->ht + table;
|
||||||
idx = h & d->ht[table].sizemask;
|
idx = h & d->ht[table].sizemask;
|
||||||
@ -570,7 +569,8 @@ dictEntry *dictFind(dict *d, const void *key)
|
|||||||
{
|
{
|
||||||
dictEntry **deT;
|
dictEntry **deT;
|
||||||
dictht *ht;
|
dictht *ht;
|
||||||
return dictFindWithPrev(d, key, &deT, &ht);
|
uint64_t h = dictHashKey(d, key);
|
||||||
|
return dictFindWithPrev(d, key, h, &deT, &ht);
|
||||||
}
|
}
|
||||||
|
|
||||||
void *dictFetchValue(dict *d, const void *key) {
|
void *dictFetchValue(dict *d, const void *key) {
|
||||||
|
@ -167,7 +167,7 @@ dictEntry *dictUnlink(dict *ht, const void *key);
|
|||||||
void dictFreeUnlinkedEntry(dict *d, dictEntry *he);
|
void dictFreeUnlinkedEntry(dict *d, dictEntry *he);
|
||||||
void dictRelease(dict *d);
|
void dictRelease(dict *d);
|
||||||
dictEntry * dictFind(dict *d, const void *key);
|
dictEntry * dictFind(dict *d, const void *key);
|
||||||
dictEntry * dictFindWithPrev(dict *d, const void *key, dictEntry ***dePrevPtr, dictht **ht);
|
dictEntry * dictFindWithPrev(dict *d, const void *key, uint64_t h, dictEntry ***dePrevPtr, dictht **ht);
|
||||||
void *dictFetchValue(dict *d, const void *key);
|
void *dictFetchValue(dict *d, const void *key);
|
||||||
int dictResize(dict *d);
|
int dictResize(dict *d);
|
||||||
dictIterator *dictGetIterator(dict *d);
|
dictIterator *dictGetIterator(dict *d);
|
||||||
|
@ -62,7 +62,10 @@ bool redisDbPersistentData::asyncDelete(robj *key) {
|
|||||||
dictEntry *de = dictUnlink(m_pdict,ptrFromObj(key));
|
dictEntry *de = dictUnlink(m_pdict,ptrFromObj(key));
|
||||||
if (de) {
|
if (de) {
|
||||||
if (m_pdbSnapshot != nullptr && m_pdbSnapshot->find_cached_threadsafe(szFromObj(key)) != nullptr)
|
if (m_pdbSnapshot != nullptr && m_pdbSnapshot->find_cached_threadsafe(szFromObj(key)) != nullptr)
|
||||||
dictAdd(m_pdictTombstone, sdsdup((sds)dictGetKey(de)), nullptr);
|
{
|
||||||
|
uint64_t hash = dictGetHash(m_pdict, szFromObj(key));
|
||||||
|
dictAdd(m_pdictTombstone, sdsdup((sds)dictGetKey(de)), (void*)hash);
|
||||||
|
}
|
||||||
|
|
||||||
robj *val = (robj*)dictGetVal(de);
|
robj *val = (robj*)dictGetVal(de);
|
||||||
if (val->FExpires())
|
if (val->FExpires())
|
||||||
|
@ -70,6 +70,7 @@ const redisDbPersistentDataSnapshot *redisDbPersistentData::createSnapshot(uint6
|
|||||||
|
|
||||||
auto spdb = std::unique_ptr<redisDbPersistentDataSnapshot>(new (MALLOC_LOCAL) redisDbPersistentDataSnapshot());
|
auto spdb = std::unique_ptr<redisDbPersistentDataSnapshot>(new (MALLOC_LOCAL) redisDbPersistentDataSnapshot());
|
||||||
|
|
||||||
|
dictRehashMilliseconds(m_pdict, 50); // Give us the best chance at a fast cleanup
|
||||||
spdb->m_fAllChanged = false;
|
spdb->m_fAllChanged = false;
|
||||||
spdb->m_fTrackingChanges = 0;
|
spdb->m_fTrackingChanges = 0;
|
||||||
spdb->m_pdict = m_pdict;
|
spdb->m_pdict = m_pdict;
|
||||||
@ -303,7 +304,7 @@ void redisDbPersistentData::endSnapshot(const redisDbPersistentDataSnapshot *psn
|
|||||||
{
|
{
|
||||||
dictEntry **dePrev;
|
dictEntry **dePrev;
|
||||||
dictht *ht;
|
dictht *ht;
|
||||||
dictEntry *deSnapshot = dictFindWithPrev(m_spdbSnapshotHOLDER->m_pdict, dictGetKey(de), &dePrev, &ht);
|
dictEntry *deSnapshot = dictFindWithPrev(m_spdbSnapshotHOLDER->m_pdict, dictGetKey(de), (uint64_t)dictGetVal(de), &dePrev, &ht);
|
||||||
if (deSnapshot == nullptr && m_spdbSnapshotHOLDER->m_pdbSnapshot)
|
if (deSnapshot == nullptr && m_spdbSnapshotHOLDER->m_pdbSnapshot)
|
||||||
{
|
{
|
||||||
// The tombstone is for a grand child, propogate it (or possibly in the storage provider - but an extra tombstone won't hurt)
|
// The tombstone is for a grand child, propogate it (or possibly in the storage provider - but an extra tombstone won't hurt)
|
||||||
|
Loading…
x
Reference in New Issue
Block a user