@@ -425,7 +425,8 @@ CacheAllocator<CacheTrait>::allocateInternalTier(TierId tid,
425425 uint32_t size,
426426 uint32_t creationTime,
427427 uint32_t expiryTime,
428- bool fromBgThread) {
428+ bool fromBgThread,
429+ bool evict) {
429430 util::LatencyTracker tracker{stats ().allocateLatency_ };
430431
431432 SCOPE_FAIL { stats_.invalidAllocs .inc (); };
@@ -446,7 +447,9 @@ CacheAllocator<CacheTrait>::allocateInternalTier(TierId tid,
446447 backgroundEvictor_[backgroundWorkerId (tid, pid, cid, backgroundEvictor_.size ())]->wakeUp ();
447448 }
448449
449- if (memory == nullptr ) {
450+ if (memory == nullptr && !evict) {
451+ return {};
452+ } else if (memory == nullptr ) {
450453 memory = findEviction (tid, pid, cid);
451454 }
452455
@@ -496,7 +499,8 @@ CacheAllocator<CacheTrait>::allocateInternal(PoolId pid,
496499 bool fromBgThread) {
497500 auto tid = 0 ; /* TODO: consult admission policy */
498501 for (TierId tid = 0 ; tid < getNumTiers (); ++tid) {
499- auto handle = allocateInternalTier (tid, pid, key, size, creationTime, expiryTime, fromBgThread);
502+ bool evict = !config_.insertToFirstFreeTier || tid == getNumTiers () - 1 ;
503+ auto handle = allocateInternalTier (tid, pid, key, size, creationTime, expiryTime, fromBgThread, evict);
500504 if (handle) return handle;
501505 }
502506 return {};
@@ -1813,13 +1817,17 @@ CacheAllocator<CacheTrait>::tryEvictToNextMemoryTier(
18131817
18141818 TierId nextTier = tid; // TODO - calculate this based on some admission policy
18151819 while (++nextTier < getNumTiers ()) { // try to evict down to the next memory tiers
1820+ // always evict item from the nextTier to make room for new item
1821+ bool evict = true ;
1822+
18161823 // allocateInternal might trigger another eviction
18171824 auto newItemHdl = allocateInternalTier (nextTier, pid,
18181825 item.getKey (),
18191826 item.getSize (),
18201827 item.getCreationTime (),
18211828 item.getExpiryTime (),
1822- fromBgThread);
1829+ fromBgThread,
1830+ evict);
18231831
18241832 if (newItemHdl) {
18251833 XDCHECK_EQ (newItemHdl->getSize (), item.getSize ());
@@ -1855,13 +1863,17 @@ CacheAllocator<CacheTrait>::tryPromoteToNextMemoryTier(
18551863 auto toPromoteTier = nextTier - 1 ;
18561864 --nextTier;
18571865
1866+ // always evict item from the toPromoteTier to make room for new item
1867+ bool evict = true ;
1868+
18581869 // allocateInternal might trigger another eviction
18591870 auto newItemHdl = allocateInternalTier (toPromoteTier, pid,
18601871 item.getKey (),
18611872 item.getSize (),
18621873 item.getCreationTime (),
18631874 item.getExpiryTime (),
1864- fromBgThread);
1875+ fromBgThread,
1876+ true );
18651877
18661878 if (newItemHdl) {
18671879 XDCHECK_EQ (newItemHdl->getSize (), item.getSize ());
@@ -3228,6 +3240,8 @@ CacheAllocator<CacheTrait>::allocateNewItemForOldItem(const Item& oldItem) {
32283240
32293241 const auto allocInfo =
32303242 allocator_[getTierId (oldItem)]->getAllocInfo (static_cast <const void *>(&oldItem));
3243+
3244+ bool evict = !config_.insertToFirstFreeTier || getTierId (oldItem) == getNumTiers () - 1 ;
32313245
32323246 // Set up the destination for the move. Since oldItem would have the moving
32333247 // bit set, it won't be picked for eviction.
@@ -3237,7 +3251,8 @@ CacheAllocator<CacheTrait>::allocateNewItemForOldItem(const Item& oldItem) {
32373251 oldItem.getSize (),
32383252 oldItem.getCreationTime (),
32393253 oldItem.getExpiryTime (),
3240- false );
3254+ false ,
3255+ evict);
32413256 if (!newItemHdl) {
32423257 return {};
32433258 }
0 commit comments