From b6d6427748cfa93b2cd242cea893f9c8eae4926a Mon Sep 17 00:00:00 2001 From: Andrey Skobtsov Date: Tue, 19 May 2020 21:22:30 +0300 Subject: [PATCH] Added file descriptors threshold --- src/Common/ThreadProfileEvents.cpp | 35 ++++++++++++++++++++++++++++++ src/Common/ThreadProfileEvents.h | 1 + 2 files changed, 36 insertions(+) diff --git a/src/Common/ThreadProfileEvents.cpp b/src/Common/ThreadProfileEvents.cpp index 2f5f41e137d..71662467870 100644 --- a/src/Common/ThreadProfileEvents.cpp +++ b/src/Common/ThreadProfileEvents.cpp @@ -12,6 +12,8 @@ #include #include #include +#include +#include namespace DB @@ -247,6 +249,39 @@ bool PerfEventsCounters::initializeThreadLocalEvents(PerfEventsCounters & counte return false; } + rlimit64 limits{}; + if (getrlimit64(RLIMIT_NOFILE, &limits)) + { + LOG_WARNING(getLogger(), "Unable to get rlimit: errno = " << errno << ", message = " << strerror(errno)); + return false; + } + UInt64 maximum_open_descriptors = limits.rlim_cur; + + std::string dir_path("/proc/"); + dir_path += std::to_string(getpid()); + dir_path += "/fd"; + DIR * fd_dir = opendir(dir_path.c_str()); + if (fd_dir == nullptr) + { + LOG_WARNING(getLogger(), "Unable to get file descriptors used by the current process errno = " << errno + << ", message = " << strerror(errno)); + return false; + } + UInt64 opened_descriptors = 0; + while (readdir(fd_dir) != nullptr) + ++opened_descriptors; + closedir(fd_dir); + + UInt64 fd_count_afterwards = opened_descriptors + NUMBER_OF_RAW_EVENTS; + UInt64 threshold = static_cast(maximum_open_descriptors * FILE_DESCRIPTORS_THRESHOLD); + if (fd_count_afterwards > threshold) + { + LOG_WARNING(getLogger(), "Can't measure perf events as the result number of file descriptors (" + << fd_count_afterwards << ") is more than the current threshold (" << threshold << " = " + << maximum_open_descriptors << " * " << FILE_DESCRIPTORS_THRESHOLD << ")"); + return false; + } + bool expected = false; bool log_unsupported_event = particular_events_unavailability_logged.compare_exchange_strong(expected, true); for (size_t i = 0; i < NUMBER_OF_RAW_EVENTS; ++i) diff --git a/src/Common/ThreadProfileEvents.h b/src/Common/ThreadProfileEvents.h index 48333632188..b0c080387d1 100644 --- a/src/Common/ThreadProfileEvents.h +++ b/src/Common/ThreadProfileEvents.h @@ -186,6 +186,7 @@ struct PerfEventsCounters typedef UInt64 Id; static constexpr size_t NUMBER_OF_RAW_EVENTS = 18; + static constexpr Float64 FILE_DESCRIPTORS_THRESHOLD = 0.7; static const PerfEventInfo raw_events_info[PerfEventsCounters::NUMBER_OF_RAW_EVENTS];