diff --git a/fdbserver/Ratekeeper.actor.cpp b/fdbserver/Ratekeeper.actor.cpp index 573feb6666..bde7ef6410 100644 --- a/fdbserver/Ratekeeper.actor.cpp +++ b/fdbserver/Ratekeeper.actor.cpp @@ -1018,6 +1018,25 @@ void StorageQueueInfo::refreshCommitCost(double elapsed) { totalWriteCosts = 0; } +Optional<double> StorageQueueInfo::getWriteQueueSizeLimitRatio(int64_t storageSpringBytes, + int64_t storageTargetBytes) const { + auto const minFreeSpace = + std::max(SERVER_KNOBS->MIN_AVAILABLE_SPACE, + (int64_t)(SERVER_KNOBS->MIN_AVAILABLE_SPACE_RATIO * smoothTotalSpace.smoothTotal())); + auto const storageQueue = getStorageQueueBytes(); + auto const springBytes = std::max<int64_t>( + 1, std::min<int64_t>(storageSpringBytes, (smoothFreeSpace.smoothTotal() - minFreeSpace) * 0.2)); + auto const targetBytes = + std::max<int64_t>(1, std::min<int64_t>(storageTargetBytes, smoothFreeSpace.smoothTotal() - minFreeSpace)); + auto const targetRateRatio = std::min((storageQueue - targetBytes + springBytes) / (double)springBytes, 2.0); + auto const inputRate = smoothInputBytes.smoothRate(); + if (targetRateRatio > 0 && inputRate > 0) { + return verySmoothDurableBytes.smoothRate() / (inputRate * targetRateRatio); + } else { + return {}; + } +} + TLogQueueInfo::TLogQueueInfo(UID id) : valid(false), id(id), smoothDurableBytes(SERVER_KNOBS->SMOOTHING_AMOUNT), smoothInputBytes(SERVER_KNOBS->SMOOTHING_AMOUNT), verySmoothDurableBytes(SERVER_KNOBS->SLOW_SMOOTHING_AMOUNT), diff --git a/fdbserver/include/fdbserver/Ratekeeper.h b/fdbserver/include/fdbserver/Ratekeeper.h index 948cca851b..a2c79cede9 100644 --- a/fdbserver/include/fdbserver/Ratekeeper.h +++ b/fdbserver/include/fdbserver/Ratekeeper.h @@ -73,6 +73,9 @@ public: int64_t getDurabilityLag() const { return smoothLatestVersion.smoothTotal() - smoothDurableVersion.smoothTotal(); } void update(StorageQueuingMetricsReply const&, Smoother& smoothTotalDurableBytes); void addCommitCost(TransactionTagRef tagName, TransactionCommitCostEstimation const& cost); + + // Determine the ratio (limit / current throughput) for throttling based on write queue size + Optional<double> getWriteQueueSizeLimitRatio(int64_t storageSpringBytes, int64_t storageTargetBytes) const; }; struct TLogQueueInfo {