Skip to content

Commit c068b63

Browse files
committed
crimson/os/cache: report dirty usage/in/out by trans and extent type
Signed-off-by: Yingxin Cheng <[email protected]>
1 parent e31058a commit c068b63

File tree

5 files changed

+202
-7
lines changed

5 files changed

+202
-7
lines changed

src/crimson/os/seastore/cache.cc

Lines changed: 96 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -146,6 +146,8 @@ void Cache::register_metrics()
146146
DEBUG("");
147147

148148
stats = {};
149+
last_dirty_io = {};
150+
last_dirty_io_by_src_ext = {};
149151

150152
namespace sm = seastar::metrics;
151153
using src_t = Transaction::src_t;
@@ -767,6 +769,7 @@ void Cache::add_to_dirty(
767769
).account_in(extent_length);
768770
if (p_src != nullptr) {
769771
assert(!is_root_type(ref->get_type()));
772+
stats.dirty_io.in_sizes.account_in(extent_length);
770773
get_by_ext(
771774
get_by_src(stats.dirty_io_by_src_ext, *p_src),
772775
ref->get_type()
@@ -790,6 +793,8 @@ void Cache::remove_from_dirty(
790793
).account_out(extent_length);
791794
if (p_src != nullptr) {
792795
assert(!is_root_type(ref->get_type()));
796+
stats.dirty_io.out_sizes.account_in(extent_length);
797+
stats.dirty_io.out_versions += ref->get_version();
793798
auto& dirty_stats = get_by_ext(
794799
get_by_src(stats.dirty_io_by_src_ext, *p_src),
795800
ref->get_type());
@@ -822,6 +827,7 @@ void Cache::replace_dirty(
822827
assert(!is_root_type(next->get_type()));
823828
assert(prev->get_type() == next->get_type());
824829

830+
stats.dirty_io.num_replace += 1;
825831
get_by_ext(
826832
get_by_src(stats.dirty_io_by_src_ext, src),
827833
next->get_type()).num_replace += 1;
@@ -2242,8 +2248,98 @@ Cache::do_get_caching_extent_by_type(
22422248
cache_stats_t Cache::get_stats(
22432249
bool report_detail, double seconds) const
22442250
{
2251+
LOG_PREFIX(Cache::get_stats);
2252+
22452253
cache_stats_t ret;
22462254
lru.get_stats(ret, report_detail, seconds);
2255+
2256+
/*
2257+
* get dirty stats
2258+
*/
2259+
2260+
ret.dirty_sizes = cache_size_stats_t{stats.dirty_bytes, dirty.size()};
2261+
ret.dirty_io = stats.dirty_io;
2262+
ret.dirty_io.minus(last_dirty_io);
2263+
2264+
if (report_detail && seconds != 0) {
2265+
counter_by_src_t<counter_by_extent_t<dirty_io_stats_t> >
2266+
_trans_io_by_src_ext = stats.dirty_io_by_src_ext;
2267+
counter_by_src_t<dirty_io_stats_t> trans_io_by_src;
2268+
for (uint8_t _src=0; _src<TRANSACTION_TYPE_MAX; ++_src) {
2269+
auto src = static_cast<transaction_type_t>(_src);
2270+
auto& io_by_ext = get_by_src(_trans_io_by_src_ext, src);
2271+
const auto& last_io_by_ext = get_by_src(last_dirty_io_by_src_ext, src);
2272+
auto& trans_io_per_src = get_by_src(trans_io_by_src, src);
2273+
for (uint8_t _ext=0; _ext<EXTENT_TYPES_MAX; ++_ext) {
2274+
auto ext = static_cast<extent_types_t>(_ext);
2275+
auto& extent_io = get_by_ext(io_by_ext, ext);
2276+
const auto& last_extent_io = get_by_ext(last_io_by_ext, ext);
2277+
extent_io.minus(last_extent_io);
2278+
trans_io_per_src.add(extent_io);
2279+
}
2280+
}
2281+
2282+
std::ostringstream oss;
2283+
oss << "\ndirty total" << ret.dirty_sizes;
2284+
cache_size_stats_t data_sizes;
2285+
cache_size_stats_t mdat_sizes;
2286+
cache_size_stats_t phys_sizes;
2287+
for (uint8_t _ext=0; _ext<EXTENT_TYPES_MAX; ++_ext) {
2288+
auto ext = static_cast<extent_types_t>(_ext);
2289+
const auto& extent_sizes = get_by_ext(stats.dirty_sizes_by_ext, ext);
2290+
2291+
if (is_data_type(ext)) {
2292+
data_sizes.add(extent_sizes);
2293+
} else if (is_logical_metadata_type(ext)) {
2294+
mdat_sizes.add(extent_sizes);
2295+
} else if (is_physical_type(ext)) {
2296+
phys_sizes.add(extent_sizes);
2297+
}
2298+
}
2299+
oss << "\n data" << data_sizes
2300+
<< "\n mdat" << mdat_sizes
2301+
<< "\n phys" << phys_sizes;
2302+
2303+
oss << "\ndirty io: "
2304+
<< dirty_io_stats_printer_t{seconds, ret.dirty_io};
2305+
for (uint8_t _src=0; _src<TRANSACTION_TYPE_MAX; ++_src) {
2306+
auto src = static_cast<transaction_type_t>(_src);
2307+
const auto& trans_io_per_src = get_by_src(trans_io_by_src, src);
2308+
if (trans_io_per_src.is_empty()) {
2309+
continue;
2310+
}
2311+
dirty_io_stats_t data_io;
2312+
dirty_io_stats_t mdat_io;
2313+
dirty_io_stats_t phys_io;
2314+
const auto& io_by_ext = get_by_src(_trans_io_by_src_ext, src);
2315+
for (uint8_t _ext=0; _ext<EXTENT_TYPES_MAX; ++_ext) {
2316+
auto ext = static_cast<extent_types_t>(_ext);
2317+
const auto extent_io = get_by_ext(io_by_ext, ext);
2318+
if (is_data_type(ext)) {
2319+
data_io.add(extent_io);
2320+
} else if (is_logical_metadata_type(ext)) {
2321+
mdat_io.add(extent_io);
2322+
} else if (is_physical_type(ext)) {
2323+
phys_io.add(extent_io);
2324+
}
2325+
}
2326+
oss << "\n " << src << ": "
2327+
<< dirty_io_stats_printer_t{seconds, trans_io_per_src}
2328+
<< "\n data: "
2329+
<< dirty_io_stats_printer_t{seconds, data_io}
2330+
<< "\n mdat: "
2331+
<< dirty_io_stats_printer_t{seconds, mdat_io}
2332+
<< "\n phys: "
2333+
<< dirty_io_stats_printer_t{seconds, phys_io};
2334+
}
2335+
2336+
INFO("{}", oss.str());
2337+
2338+
last_dirty_io_by_src_ext = stats.dirty_io_by_src_ext;
2339+
}
2340+
2341+
last_dirty_io = stats.dirty_io;
2342+
22472343
return ret;
22482344
}
22492345

src/crimson/os/seastore/cache.h

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1605,6 +1605,7 @@ class Cache {
16051605

16061606
uint64_t dirty_bytes = 0;
16071607
counter_by_extent_t<cache_size_stats_t> dirty_sizes_by_ext;
1608+
dirty_io_stats_t dirty_io;
16081609
counter_by_src_t<counter_by_extent_t<dirty_io_stats_t> >
16091610
dirty_io_by_src_ext;
16101611

@@ -1635,6 +1636,10 @@ class Cache {
16351636
version_stat_t committed_reclaim_version;
16361637
} stats;
16371638

1639+
mutable dirty_io_stats_t last_dirty_io;
1640+
mutable counter_by_src_t<counter_by_extent_t<dirty_io_stats_t> >
1641+
last_dirty_io_by_src_ext;
1642+
16381643
void account_conflict(Transaction::src_t src1, Transaction::src_t src2) {
16391644
assert(src1 < Transaction::src_t::MAX);
16401645
assert(src2 < Transaction::src_t::MAX);

src/crimson/os/seastore/seastore.cc

Lines changed: 18 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -705,6 +705,7 @@ seastar::future<> SeaStore::report_stats()
705705
for (const auto& s : shard_cache_stats) {
706706
cache_total.add(s);
707707
}
708+
708709
cache_size_stats_t lru_sizes_ps = cache_total.lru_sizes;
709710
lru_sizes_ps.size /= seastar::smp::count;
710711
lru_sizes_ps.num_extents /= seastar::smp::count;
@@ -718,6 +719,23 @@ seastar::future<> SeaStore::report_stats()
718719
cache_io_stats_printer_t{seconds, cache_total.lru_io},
719720
lru_sizes_ps,
720721
cache_io_stats_printer_t{seconds, lru_io_ps});
722+
723+
cache_size_stats_t dirty_sizes_ps = cache_total.dirty_sizes;
724+
dirty_sizes_ps.size /= seastar::smp::count;
725+
dirty_sizes_ps.num_extents /= seastar::smp::count;
726+
dirty_io_stats_t dirty_io_ps = cache_total.dirty_io;
727+
dirty_io_ps.in_sizes.size /= seastar::smp::count;
728+
dirty_io_ps.in_sizes.num_extents /= seastar::smp::count;
729+
dirty_io_ps.num_replace /= seastar::smp::count;
730+
dirty_io_ps.out_sizes.size /= seastar::smp::count;
731+
dirty_io_ps.out_sizes.num_extents /= seastar::smp::count;
732+
dirty_io_ps.out_versions /= seastar::smp::count;
733+
INFO("cache dirty: total{} {}; per-shard: total{} {}",
734+
cache_total.dirty_sizes,
735+
dirty_io_stats_printer_t{seconds, cache_total.dirty_io},
736+
dirty_sizes_ps,
737+
dirty_io_stats_printer_t{seconds, dirty_io_ps});
738+
721739
return seastar::now();
722740
});
723741
}

src/crimson/os/seastore/seastore_types.cc

Lines changed: 27 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1012,4 +1012,31 @@ std::ostream& operator<<(std::ostream& out, const cache_size_stats_t& p)
10121012
return out;
10131013
}
10141014

1015+
std::ostream& operator<<(std::ostream& out, const cache_size_stats_printer_t& p)
1016+
{
1017+
constexpr const char* dfmt = "{:.2f}";
1018+
out << "("
1019+
<< fmt::format(dfmt, p.stats.get_mb()/p.seconds)
1020+
<< "MiB/s,"
1021+
<< fmt::format(dfmt, p.stats.get_avg_kb())
1022+
<< "KiB,"
1023+
<< fmt::format(dfmt, p.stats.num_extents/p.seconds)
1024+
<< "ps)";
1025+
return out;
1026+
}
1027+
1028+
std::ostream& operator<<(std::ostream& out, const dirty_io_stats_printer_t& p)
1029+
{
1030+
constexpr const char* dfmt = "{:.2f}";
1031+
out << "in"
1032+
<< cache_size_stats_printer_t{p.seconds, p.stats.in_sizes}
1033+
<< " replaces="
1034+
<< fmt::format(dfmt, p.stats.num_replace/p.seconds)
1035+
<< "ps out"
1036+
<< cache_size_stats_printer_t{p.seconds, p.stats.out_sizes}
1037+
<< " outv="
1038+
<< fmt::format(dfmt, p.stats.get_avg_out_version());
1039+
return out;
1040+
}
1041+
10151042
} // namespace crimson::os::seastore

src/crimson/os/seastore/seastore_types.h

Lines changed: 56 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -2617,6 +2617,10 @@ struct cache_size_stats_t {
26172617
uint64_t size = 0;
26182618
uint64_t num_extents = 0;
26192619

2620+
bool is_empty() const {
2621+
return num_extents == 0;
2622+
}
2623+
26202624
double get_mb() const {
26212625
return (size>>12)/static_cast<double>(256);
26222626
}
@@ -2641,26 +2645,69 @@ struct cache_size_stats_t {
26412645
size += o.size;
26422646
num_extents += o.num_extents;
26432647
}
2648+
2649+
void minus(const cache_size_stats_t& o) {
2650+
size -= o.size;
2651+
num_extents -= o.num_extents;
2652+
}
26442653
};
26452654
std::ostream& operator<<(std::ostream&, const cache_size_stats_t&);
2655+
struct cache_size_stats_printer_t {
2656+
double seconds;
2657+
const cache_size_stats_t& stats;
2658+
};
2659+
std::ostream& operator<<(std::ostream&, const cache_size_stats_printer_t&);
2660+
2661+
struct dirty_io_stats_t {
2662+
cache_size_stats_t in_sizes;
2663+
uint64_t num_replace = 0;
2664+
cache_size_stats_t out_sizes;
2665+
uint64_t out_versions = 0;
2666+
2667+
double get_avg_out_version() const {
2668+
return out_versions/static_cast<double>(out_sizes.num_extents);
2669+
}
2670+
2671+
bool is_empty() const {
2672+
return in_sizes.is_empty() &&
2673+
num_replace == 0 &&
2674+
out_sizes.is_empty();
2675+
}
2676+
2677+
void add(const dirty_io_stats_t& o) {
2678+
in_sizes.add(o.in_sizes);
2679+
num_replace += o.num_replace;
2680+
out_sizes.add(o.out_sizes);
2681+
out_versions += o.out_versions;
2682+
}
2683+
2684+
void minus(const dirty_io_stats_t& o) {
2685+
in_sizes.minus(o.in_sizes);
2686+
num_replace -= o.num_replace;
2687+
out_sizes.minus(o.out_sizes);
2688+
out_versions -= o.out_versions;
2689+
}
2690+
};
2691+
struct dirty_io_stats_printer_t {
2692+
double seconds;
2693+
const dirty_io_stats_t& stats;
2694+
};
2695+
std::ostream& operator<<(std::ostream&, const dirty_io_stats_printer_t&);
26462696

26472697
struct cache_stats_t {
26482698
cache_size_stats_t lru_sizes;
26492699
cache_io_stats_t lru_io;
2700+
cache_size_stats_t dirty_sizes;
2701+
dirty_io_stats_t dirty_io;
26502702

26512703
void add(const cache_stats_t& o) {
26522704
lru_sizes.add(o.lru_sizes);
26532705
lru_io.add(o.lru_io);
2706+
dirty_sizes.add(o.dirty_sizes);
2707+
dirty_io.add(o.dirty_io);
26542708
}
26552709
};
26562710

2657-
struct dirty_io_stats_t {
2658-
cache_size_stats_t in_sizes;
2659-
uint64_t num_replace = 0;
2660-
cache_size_stats_t out_sizes;
2661-
uint64_t out_versions = 0;
2662-
};
2663-
26642711
}
26652712

26662713
WRITE_CLASS_DENC_BOUNDED(crimson::os::seastore::seastore_meta_t)
@@ -2680,9 +2727,11 @@ WRITE_CLASS_DENC_BOUNDED(crimson::os::seastore::segment_tail_t)
26802727
#if FMT_VERSION >= 90000
26812728
template <> struct fmt::formatter<crimson::os::seastore::cache_io_stats_printer_t> : fmt::ostream_formatter {};
26822729
template <> struct fmt::formatter<crimson::os::seastore::cache_size_stats_t> : fmt::ostream_formatter {};
2730+
template <> struct fmt::formatter<crimson::os::seastore::cache_size_stats_printer_t> : fmt::ostream_formatter {};
26832731
template <> struct fmt::formatter<crimson::os::seastore::data_category_t> : fmt::ostream_formatter {};
26842732
template <> struct fmt::formatter<crimson::os::seastore::delta_info_t> : fmt::ostream_formatter {};
26852733
template <> struct fmt::formatter<crimson::os::seastore::device_id_printer_t> : fmt::ostream_formatter {};
2734+
template <> struct fmt::formatter<crimson::os::seastore::dirty_io_stats_printer_t> : fmt::ostream_formatter {};
26862735
template <> struct fmt::formatter<crimson::os::seastore::extent_types_t> : fmt::ostream_formatter {};
26872736
template <> struct fmt::formatter<crimson::os::seastore::journal_seq_t> : fmt::ostream_formatter {};
26882737
template <> struct fmt::formatter<crimson::os::seastore::journal_tail_delta_t> : fmt::ostream_formatter {};

0 commit comments

Comments
 (0)