@@ -207,7 +207,7 @@ class STBucketQuotaTest : public STParameterizedBucketTest {
207207 {
208208 auto key = makeStoredDocKey (std::string (keyPrefix) +
209209 std::to_string (count++));
210- auto item = make_item (vbid, key, std::string (100 , ' x' ));
210+ auto item = make_item (vbid, key, std::string (5000 , ' x' ));
211211 // make the items have a range of MFU values
212212 // without this, no matter what percent of items should be
213213 // evicted, either all of them or none of them would be
@@ -220,8 +220,12 @@ class STBucketQuotaTest : public STParameterizedBucketTest {
220220 mfu = ht.generateFreqValue (mfu);
221221 }
222222 item.setFreqCounterValue (mfu);
223- EXPECT_EQ (ENGINE_SUCCESS, storeItem (item));
224- flushAndRemoveCheckpoints (vbid);
223+ auto result = storeItem (item);
224+ if (result != ENGINE_SUCCESS) {
225+ ADD_FAILURE () << " Failed storing an item before the "
226+ " predicate returned true" ;
227+ return count;
228+ }
225229 }
226230 populate = !predicate ();
227231 if (!populate) {
@@ -909,12 +913,17 @@ TEST_P(STItemPagerTest, ReplicaEvictedBeforeActive) {
909913 // greater than the gap between high and low watermarks. With the default
910914 // quota, there's not enough "headroom" left after base memory usage to
911915 // populate vbs as desired.
912- increaseQuota (2100000 );
916+ increaseQuota (2200000 );
913917
914918 auto & stats = engine->getEpStats ();
915919
916920 auto watermarkDiff = stats.mem_high_wat .load () - stats.mem_low_wat .load ();
917921
922+ // starting above the low water mark would mean that the replica pageable
923+ // memory will definitely not exceed the watermarkdiff when the high
924+ // watermark is reached.
925+ ASSERT_LT (stats.getPreciseTotalMemoryUsed (), stats.mem_low_wat .load ());
926+
918927 // populate the replica vbs until its evictable memory _exceeds_ the gap
919928 // between the high and low water mark. When the mem usage later passes the
920929 // high water mark, evicting from the replica should reclaim enough memory.
@@ -934,8 +943,10 @@ TEST_P(STItemPagerTest, ReplicaEvictedBeforeActive) {
934943 // replicas, their total pageable memory must be at least the
935944 // watermark diff + a small excess to account for the final
936945 // inserted item _passing_ the high watermark.
937- return pageableMem > watermarkDiff * 1.1 ;
946+ return pageableMem > watermarkDiff + 10000 ;
938947 });
948+ flushAndRemoveCheckpoints (replicaVBs[0 ]);
949+ flushAndRemoveCheckpoints (replicaVBs[1 ]);
939950
940951 // We don't care exactly how many were stored, just that it is a
941952 // "large enough" number for percentages to be somewhat useful
@@ -944,6 +955,20 @@ TEST_P(STItemPagerTest, ReplicaEvictedBeforeActive) {
944955 // Now fill the active VB until the high watermark is reached
945956 auto activeItemCount =
946957 populateVbsUntil (activeVBs, [&stats, &store = store] {
958+ return stats.getPreciseTotalMemoryUsed () >
959+ stats.mem_high_wat .load ();
960+ });
961+
962+ flushAndRemoveCheckpoints (activeVBs[0 ]);
963+ flushAndRemoveCheckpoints (activeVBs[1 ]);
964+
965+ // Flushing and removing checkpoints frees some memory, "top up" the
966+ // active vbuckets back to the high watermark.
967+ activeItemCount += populateVbsUntil (
968+ activeVBs,
969+ [this , &stats, &activeVBs] {
970+ flushAndRemoveCheckpoints (activeVBs[0 ]);
971+ flushAndRemoveCheckpoints (activeVBs[1 ]);
947972 bool readyToEvict = stats.getPreciseTotalMemoryUsed () >
948973 stats.mem_high_wat .load ();
949974 if (readyToEvict) {
@@ -954,7 +979,8 @@ TEST_P(STItemPagerTest, ReplicaEvictedBeforeActive) {
954979 store->attemptToFreeMemory ();
955980 }
956981 return readyToEvict;
957- });
982+ },
983+ " topup_keys" );
958984
959985 EXPECT_GT (activeItemCount, 100 );
960986
@@ -983,11 +1009,11 @@ TEST_P(STItemPagerTest, ReplicaEvictedBeforeActive) {
9831009 << vbid << " not fully resident after eviction" ;
9841010 }
9851011 // Confirm the replica RR is "low"
986- // the replica RR could be constrained further (around 5%) but checking
987- // it is below 10 % to avoid making the test too sensitive to small
1012+ // the replica RR could be constrained further, but checking
1013+ // it is below 20 % to avoid making the test too sensitive to small
9881014 // changes in base memory usage.
9891015 for (const auto vbid : replicaVBs) {
990- EXPECT_LT (getRRPercent (*store->getVBucket (vbid)), 10 )
1016+ EXPECT_LT (getRRPercent (*store->getVBucket (vbid)), 20 )
9911017 << vbid << " has residency higher than expected" ;
9921018 }
9931019}
@@ -1017,28 +1043,36 @@ TEST_P(STItemPagerTest, ActiveEvictedIfReplicaEvictionInsufficient) {
10171043 // Set replicaVB as active initially (so we can populate it).
10181044 setVBucketStateAndRunPersistTask (replicaVB, vbucket_state_active);
10191045
1020- // We need total evictable data to comfortably exceed the gap between
1021- // high and low watermarks. With the default quota, there's not enough
1022- // "headroom" left after base memory usage to populate vbs as desired.
1023- increaseQuota (1200000 );
1024- auto quota = engine->getConfiguration ().getMaxSize ();
1025-
1026- // Set the water marks to 80% and 85%
1027- engine->getConfiguration ().setMemLowWat (quota * 0.80 );
1028- engine->getConfiguration ().setMemHighWat (quota * 0.85 );
1046+ // bump the quota up. We need total evictable data to comfortably exceed
1047+ // the gap between high and low watermarks. With the default
1048+ // quota, there's not enough "headroom" left after base memory usage to
1049+ // populate vbs as desired.
1050+ increaseQuota (20000000 );
10291051
10301052 auto & stats = engine->getEpStats ();
10311053
1032- auto targetReplicaMem =
1033- stats.getPreciseTotalMemoryUsed () +
1034- double (stats.mem_high_wat .load () - stats.mem_low_wat .load ()) * 0.9 ;
1054+ auto watermarkDiff = stats.mem_high_wat .load () - stats.mem_low_wat .load ();
1055+
1056+ // starting above the low water mark would mean that the replica pageable
1057+ // memory will definitely not exceed the watermarkdiff when the high
1058+ // watermark is reached.
1059+ ASSERT_LT (stats.getPreciseTotalMemoryUsed (), stats.mem_low_wat .load ());
10351060
10361061 // store items in the replica vb such that evicting everything in the
10371062 // replica when at the high watermark will _not_ reach the low watermark
1038- auto replicaItemCount =
1039- populateVbsUntil ({replicaVB}, [&stats, targetReplicaMem] {
1040- return stats.getPreciseTotalMemoryUsed () >= targetReplicaMem;
1063+ auto replicaItemCount = populateVbsUntil (
1064+ {replicaVB}, [&stats, &store = store, replicaVB, watermarkDiff] {
1065+ // sanity check - if this fails the quota is too low -
1066+ EXPECT_LT (stats.getPreciseTotalMemoryUsed (),
1067+ stats.mem_high_wat .load ());
1068+
1069+ size_t pageableMem =
1070+ store->getVBucket (replicaVB)->getPageableMemUsage ();
1071+
1072+ return pageableMem > watermarkDiff * 0.8 ;
10411073 });
1074+ flushAndRemoveCheckpoints (replicaVB);
1075+
10421076 setVBucketStateAndRunPersistTask (replicaVB, vbucket_state_replica);
10431077
10441078 // We don't care exactly how many were stored, just that it is a
@@ -1048,6 +1082,18 @@ TEST_P(STItemPagerTest, ActiveEvictedIfReplicaEvictionInsufficient) {
10481082 // Now fill the active VB until the high watermark is reached
10491083 auto activeItemCount =
10501084 populateVbsUntil ({activeVB}, [&stats, &store = store] {
1085+ return stats.getPreciseTotalMemoryUsed () >
1086+ stats.mem_high_wat .load ();
1087+ });
1088+
1089+ flushAndRemoveCheckpoints (activeVB);
1090+
1091+ // Flushing and removing checkpoints frees some memory, "top up" the
1092+ // active vbuckets back to the high watermark.
1093+ activeItemCount += populateVbsUntil (
1094+ {activeVB},
1095+ [this , &stats, &activeVB] {
1096+ flushAndRemoveCheckpoints (activeVB);
10511097 bool readyToEvict = stats.getPreciseTotalMemoryUsed () >
10521098 stats.mem_high_wat .load ();
10531099 if (readyToEvict) {
@@ -1058,7 +1104,8 @@ TEST_P(STItemPagerTest, ActiveEvictedIfReplicaEvictionInsufficient) {
10581104 store->attemptToFreeMemory ();
10591105 }
10601106 return readyToEvict;
1061- });
1107+ },
1108+ " topup_keys" );
10621109
10631110 EXPECT_GT (activeItemCount, 100 );
10641111
0 commit comments