From 289aca0c4a6d95ccce824a3c14748158620c826a Mon Sep 17 00:00:00 2001 From: Jason Volk Date: Thu, 28 Mar 2019 17:09:46 -0700 Subject: [PATCH] ircd::ios: Move descriptor stats into structure. --- include/ircd/ios.h | 29 +++++++++++++------ ircd/ios.cc | 70 ++++++++++++++++++++++++++++++++++++++-------- modules/console.cc | 24 ++++++++++------ 3 files changed, 94 insertions(+), 29 deletions(-) diff --git a/include/ircd/ios.h b/include/ircd/ios.h index c8267b2bb..0c85abea1 100644 --- a/include/ircd/ios.h +++ b/include/ircd/ios.h @@ -68,6 +68,8 @@ namespace ircd struct ircd::ios::descriptor :instance_list { + struct stats; + static uint64_t ids; static void *default_allocator(handler &, const size_t &); @@ -75,15 +77,7 @@ struct ircd::ios::descriptor string_view name; uint64_t id {++ids}; - uint64_t calls {0}; - uint64_t faults {0}; - uint64_t allocs {0}; - uint64_t alloc_bytes{0}; - uint64_t frees {0}; - uint64_t free_bytes{0}; - uint64_t slice_total {0}; - uint64_t slice_last {0}; - + std::unique_ptr stats; std::function allocator; std::function deallocator; bool continuation; @@ -98,6 +92,23 @@ struct ircd::ios::descriptor ~descriptor() noexcept; }; +struct ircd::ios::descriptor::stats +{ + uint64_t calls {0}; + uint64_t faults {0}; + uint64_t allocs {0}; + uint64_t alloc_bytes{0}; + uint64_t frees {0}; + uint64_t free_bytes{0}; + uint64_t slice_total {0}; + uint64_t slice_last {0}; + + stats &operator+=(const stats &) &; + + stats(); + ~stats() noexcept; +}; + struct ircd::ios::handler { static thread_local handler *current; diff --git a/ircd/ios.cc b/ircd/ios.cc index 83560c821..fe1206c69 100644 --- a/ircd/ios.cc +++ b/ircd/ios.cc @@ -129,6 +129,7 @@ ircd::ios::descriptor::descriptor(const string_view &name, const decltype(deallocator) &deallocator, const bool &continuation) :name{name} +,stats{std::make_unique()} ,allocator{allocator} ,deallocator{deallocator} ,continuation{continuation} @@ -157,6 +158,34 @@ ircd::ios::descriptor::default_allocator(handler &handler, return ::operator new(size); } +// +// descriptor::stats +// + +ircd::ios::descriptor::stats::stats() +{ +} + +ircd::ios::descriptor::stats::~stats() +noexcept +{ +} + +ircd::ios::descriptor::stats & +ircd::ios::descriptor::stats::operator+=(const stats &o) +& +{ + calls += o.calls; + faults += o.faults; + allocs += o.allocs; + alloc_bytes += o.alloc_bytes; + frees += o.frees; + free_bytes += o.free_bytes; + slice_total += o.slice_total; + slice_last += o.slice_last; + return *this; +} + // // handler // @@ -169,15 +198,18 @@ ircd::ios::handler::fault(handler *const &handler) { assert(handler && handler->descriptor); auto &descriptor(*handler->descriptor); - ++descriptor.faults; - bool ret(false); + assert(descriptor.stats); + auto &stats(*descriptor.stats); + ++stats.faults; + + bool ret(false); // leave() isn't called if we return false so the tsc counter // needs to be tied off here instead. if(!ret) { - descriptor.slice_last = cycles() - handler->slice_start; - descriptor.slice_total += descriptor.slice_last; + stats.slice_last = cycles() - handler->slice_start; + stats.slice_total += stats.slice_last; } return ret; @@ -188,8 +220,12 @@ ircd::ios::handler::leave(handler *const &handler) { assert(handler && handler->descriptor); auto &descriptor(*handler->descriptor); - descriptor.slice_last = cycles() - handler->slice_start; - descriptor.slice_total += descriptor.slice_last; + + assert(descriptor.stats); + auto &stats(*descriptor.stats); + stats.slice_last = cycles() - handler->slice_start; + stats.slice_total += stats.slice_last; + assert(handler::current == handler); handler::current = nullptr; } @@ -199,7 +235,11 @@ ircd::ios::handler::enter(handler *const &handler) { assert(handler && handler->descriptor); auto &descriptor(*handler->descriptor); - ++descriptor.calls; + + assert(descriptor.stats); + auto &stats(*descriptor.stats); + ++stats.calls; + assert(!handler::current); handler::current = handler; handler->slice_start = cycles(); @@ -220,9 +260,13 @@ ircd::ios::handler::deallocate(handler *const &handler, { assert(handler && handler->descriptor); auto &descriptor(*handler->descriptor); + descriptor.deallocator(*handler, ptr, size); - descriptor.free_bytes += size; - ++descriptor.frees; + + assert(descriptor.stats); + auto &stats(*descriptor.stats); + stats.free_bytes += size; + ++stats.frees; } void * @@ -231,7 +275,11 @@ ircd::ios::handler::allocate(handler *const &handler, { assert(handler && handler->descriptor); auto &descriptor(*handler->descriptor); - descriptor.alloc_bytes += size; - ++descriptor.allocs; + + assert(descriptor.stats); + auto &stats(*descriptor.stats); + stats.alloc_bytes += size; + ++stats.allocs; + return descriptor.allocator(*handler, size); } diff --git a/modules/console.cc b/modules/console.cc index 28d9a1cb3..c5a8fb1af 100644 --- a/modules/console.cc +++ b/modules/console.cc @@ -830,13 +830,14 @@ console_cmd__ios(opt &out, const string_view &line) { out << std::left << std::setw(3) << "ID" << " " << std::left << std::setw(48) << "NAME" - << " " << std::right << std::setw(6) << "FAULTS" << " " << std::right << std::setw(10) << "CALLS" - << " " << std::right << std::setw(15) << "CYCLES" + << " " << std::right << std::setw(15) << "TOTAL CYCLES" + << " " << std::right << std::setw(15) << "LAST CYCLES" << " " << std::right << std::setw(10) << "ALLOCS" << " " << std::right << std::setw(10) << "FREES" << " " << std::right << std::setw(26) << "ALLOCATED" << " " << std::right << std::setw(26) << "FREED" + << " " << std::right << std::setw(6) << "FAULTS" << std::endl ; @@ -844,16 +845,21 @@ console_cmd__ios(opt &out, const string_view &line) { assert(descriptor); const auto &d(*descriptor); + + assert(d.stats); + const auto &s(*d.stats); + thread_local char pbuf[64]; out << std::left << std::setw(3) << d.id << " " << std::left << std::setw(48) << d.name - << " " << std::right << std::setw(6) << d.faults - << " " << std::right << std::setw(10) << d.calls - << " " << std::right << std::setw(15) << d.slice_total - << " " << std::right << std::setw(10) << d.allocs - << " " << std::right << std::setw(10) << d.frees - << " " << std::right << std::setw(26) << pretty(iec(d.alloc_bytes)) - << " " << std::right << std::setw(26) << pretty(iec(d.free_bytes)) + << " " << std::right << std::setw(10) << s.calls + << " " << std::right << std::setw(15) << s.slice_total + << " " << std::right << std::setw(15) << s.slice_last + << " " << std::right << std::setw(10) << s.allocs + << " " << std::right << std::setw(10) << s.frees + << " " << std::right << std::setw(26) << pretty(iec(s.alloc_bytes)) + << " " << std::right << std::setw(26) << pretty(iec(s.free_bytes)) + << " " << std::right << std::setw(6) << s.faults << std::endl ; }