diff --git a/include/ircd/prof/psi.h b/include/ircd/prof/psi.h index 5325f22a1..459279e53 100644 --- a/include/ircd/prof/psi.h +++ b/include/ircd/prof/psi.h @@ -17,8 +17,12 @@ namespace ircd::prof::psi struct metric; struct refresh; + // Read and update the referenced extern. bool refresh(file &) noexcept; + // Yield ircd::ctx until event; returns unrefreshed + file &wait(); + extern const bool supported; extern file cpu, mem, io; } diff --git a/ircd/prof_linux.cc b/ircd/prof_linux.cc index d66c889d5..2ee7b5b49 100644 --- a/ircd/prof_linux.cc +++ b/ircd/prof_linux.cc @@ -188,6 +188,47 @@ ircd::prof::psi::io // prof::psi::metric::refresh // +ircd::prof::psi::file & +ircd::prof::psi::wait() +try +{ + const fs::fd fd[3] + { + { "/proc/pressure/cpu", std::ios::in }, + { "/proc/pressure/memory", std::ios::in }, + { "/proc/pressure/io", std::ios::in }, + }; + + const size_t n + { + fs::select(fd) + }; + + switch(n) + { + case 0: return cpu; + case 1: return mem; + case 2: return io; + default: + always_assert(false); + __builtin_unreachable(); + } +} +catch(const ctx::interrupted &) +{ + throw; +} +catch(const std::exception &e) +{ + log::error + { + "Failed to poll pressure stall information :%s", + e.what(), + }; + + throw; +} + bool ircd::prof::psi::refresh(file &file) noexcept try diff --git a/modules/console.cc b/modules/console.cc index 583803b7b..76c1ddbeb 100644 --- a/modules/console.cc +++ b/modules/console.cc @@ -1278,9 +1278,33 @@ console_cmd__prof__psi(opt &out, const string_view &line) out << std::endl; }}; - show_file("cpu", prof::psi::cpu); - show_file("mem", prof::psi::mem); - show_file("io ", prof::psi::io); + const params param{line, " ", + { + "file", + }}; + + string_view filename + { + param["file"] + }; + + if(filename == "wait") + { + auto &file(prof::psi::wait()); + out << "Got: " << file.name; + out << std::endl << std::endl; + filename = file.name; + } + + if(!filename || filename == "cpu") + show_file("cpu", prof::psi::cpu); + + if(!filename || filename == "mem") + show_file("mem", prof::psi::mem); + + if(!filename || filename == "io") + show_file("io ", prof::psi::io); + return true; }