if (txc->had_ios)
kv_ios++;
kv_throttle_costs += txc->cost;
+ ++kv_throttle_txcs;
}
return;
case TransContext::STATE_KV_SUBMITTED:
", txc cost = " + stringify(txc->cost) +
", txc onodes = " + stringify(txc->onodes.size()) +
", DB updates = " + stringify(txc->t->get_count()) +
- ", DB bytes = " + stringify(txc->t->get_size_bytes())
+ ", DB bytes = " + stringify(txc->t->get_size_bytes()) +
+ ", cost max = " + stringify(throttle.bytes_observed_max) +
+ " on " + stringify(throttle.bytes_max_ts) +
+ ", txc max = " + stringify(throttle.transactions_observed_max) +
+ " on " + stringify(throttle.transactions_max_ts)
;
},
l_bluestore_slow_committed_kv_count
} else {
deque<TransContext*> kv_submitting;
deque<DeferredBatch*> deferred_done, deferred_stable;
- uint64_t aios = 0, costs = 0;
+ uint64_t aios = 0, costs = 0, txcs = 0;
dout(20) << __func__ << " committing " << kv_queue.size()
<< " submitting " << kv_queue_unsubmitted.size()
deferred_stable.swap(deferred_stable_queue);
aios = kv_ios;
costs = kv_throttle_costs;
+ txcs = kv_throttle_txcs;
kv_ios = 0;
kv_throttle_costs = 0;
+ kv_throttle_txcs = 0;
l.unlock();
dout(30) << __func__ << " committing " << kv_committing << dendl;
// iteration there will already be ops awake. otherwise, we
// end up going to sleep, and then wake up when the very first
// transaction is ready for commit.
- throttle.release_kv_throttle(costs);
+ throttle.release_kv_throttle(costs, txcs);
// cleanup sync deferred keys
for (auto b : deferred_stable) {
TransContext &txc,
mono_clock::time_point start_throttle_acquire)
{
+ {
+ std::lock_guard l(lock);
+ auto cost0 = throttle_bytes.get_current();
+ if (cost0 + txc.cost > bytes_observed_max) {
+ bytes_observed_max = cost0 + txc.cost;
+ bytes_max_ts = ceph_clock_now();
+ }
+ auto txcs = ++transactions;
+ if (txcs > transactions_observed_max) {
+ transactions_observed_max = txcs;
+ transactions_max_ts = ceph_clock_now();
+ }
+ }
+
throttle_bytes.get(txc.cost);
if (!txc.deferred_txn || throttle_deferred_bytes.get_or_fail(txc.cost)) {
Throttle throttle_bytes; ///< submit to commit
Throttle throttle_deferred_bytes; ///< submit to deferred complete
+ public:
+ ceph::mutex lock = ceph::make_mutex("BlueStoreThrottle::max_lock");
+
+ std::atomic<uint64_t> transactions = 0;
+
+ int64_t bytes_observed_max = 0;
+ utime_t bytes_max_ts;
+ uint64_t transactions_observed_max = 0;
+ utime_t transactions_max_ts;
+
+ uint64_t get_current() {
+ return throttle_bytes.get_current();
+ }
+
public:
BlueStoreThrottle(CephContext *cct) :
throttle_bytes(cct, "bluestore_throttle_bytes", 0),
KeyValueDB &db,
TransContext &txc,
ceph::mono_clock::time_point);
- void release_kv_throttle(uint64_t cost) {
+ void release_kv_throttle(uint64_t cost, uint64_t txcs) {
throttle_bytes.put(cost);
+ transactions -= txcs;
}
void release_deferred_throttle(uint64_t cost) {
throttle_deferred_bytes.put(cost);
uint64_t kv_ios = 0;
uint64_t kv_throttle_costs = 0;
+ uint64_t kv_throttle_txcs = 0;
// cache trim control
uint64_t cache_size = 0; ///< total cache size