diff options
author | dormando <dormando@rydia.net> | 2017-01-09 01:03:09 -0800 |
---|---|---|
committer | dormando <dormando@rydia.net> | 2017-01-22 19:47:50 -0800 |
commit | ea773779cdf8621c4d1ca13fed2fff4c239d3608 (patch) | |
tree | 1f1e915a686b2ffd4f522453623e0a703e5ee393 /slabs.c | |
parent | dcdcd8a551e4af2210b750bc848ec7daf967d938 (diff) | |
download | memcached-ea773779cdf8621c4d1ca13fed2fff4c239d3608.tar.gz |
stop using atomics for item refcount management
when I first split the locks up further I had a trick where "item_remove()"
did not require holding the associated item lock. If an item were to be freed,
it would then do the necessary work.;
Since then, all calls to refcount_incr and refcount_decr only happen while the
item is locked. This was mostly due to the slab mover being very tricky with
locks. The atomic is no longer needed as the refcount is only ever checked
after a lock to the item.
Calling atomics is pretty expensive, especially in multicore/multisocket
scenarios. This yields a notable performance increase.
Diffstat (limited to 'slabs.c')
-rw-r--r-- | slabs.c | 6 |
1 files changed, 3 insertions, 3 deletions
@@ -823,7 +823,7 @@ static int slab_rebalance_move(void) { if ((hold_lock = item_trylock(hv)) == NULL) { status = MOVE_LOCKED; } else { - refcount = refcount_incr(&it->refcount); + refcount = refcount_incr(it); if (refcount == 2) { /* item is linked but not busy */ /* Double check ITEM_LINKED flag here, since we're * past a memory barrier from the mutex. */ @@ -844,7 +844,7 @@ static int slab_rebalance_move(void) { } /* Item lock must be held while modifying refcount */ if (status == MOVE_BUSY) { - refcount_decr(&it->refcount); + refcount_decr(it); item_trylock_unlock(hold_lock); } } @@ -935,7 +935,7 @@ static int slab_rebalance_move(void) { #ifdef DEBUG_SLAB_MOVER memcpy(ITEM_key((item *)ch), "deadbeef", 8); #endif - refcount_decr(&it->refcount); + refcount_decr(it); requested_adjust = s_cls->size; } } else { |