diff options
author | Daniil Cherednik <dan.cherednik@gmail.com> | 2022-09-21 20:17:38 +0300 |
---|---|---|
committer | Daniil Cherednik <dan.cherednik@gmail.com> | 2022-09-21 20:17:38 +0300 |
commit | e6c9b17192c56494adba359d5e132c431b241191 (patch) | |
tree | 6f2449871a118a0e8919ce842b1174e06cb470ef /util | |
parent | 285021ab1aac39e84b269d9bacd4deee69cf63fc (diff) | |
download | ydb-e6c9b17192c56494adba359d5e132c431b241191.tar.gz |
Ydb stable 22-4-2122.4.21
x-stable-origin-commit: e89099581237299a132feafb5b58af59ebd0468a
Diffstat (limited to 'util')
-rw-r--r-- | util/CMakeLists.darwin.txt | 2 | ||||
-rw-r--r-- | util/CMakeLists.linux.txt | 2 | ||||
-rw-r--r-- | util/CMakeLists.txt | 2 | ||||
-rw-r--r-- | util/datetime/cputimer.cpp | 17 | ||||
-rw-r--r-- | util/datetime/cputimer.h | 4 | ||||
-rw-r--r-- | util/datetime/cputimer_ut.cpp | 10 | ||||
-rw-r--r-- | util/system/hostname.cpp | 37 |
7 files changed, 64 insertions, 10 deletions
diff --git a/util/CMakeLists.darwin.txt b/util/CMakeLists.darwin.txt index 99dd3df2e9..2d6f8d3256 100644 --- a/util/CMakeLists.darwin.txt +++ b/util/CMakeLists.darwin.txt @@ -7,6 +7,8 @@ find_package(ZLIB REQUIRED) +add_subdirectory(charset) +add_subdirectory(draft) add_library(yutil) target_compile_options(yutil PRIVATE diff --git a/util/CMakeLists.linux.txt b/util/CMakeLists.linux.txt index f3035c0bb1..406d454b11 100644 --- a/util/CMakeLists.linux.txt +++ b/util/CMakeLists.linux.txt @@ -7,6 +7,8 @@ find_package(ZLIB REQUIRED) +add_subdirectory(charset) +add_subdirectory(draft) add_library(yutil) target_compile_options(yutil PRIVATE diff --git a/util/CMakeLists.txt b/util/CMakeLists.txt index fc7b1ee73c..dbfe6fa2c4 100644 --- a/util/CMakeLists.txt +++ b/util/CMakeLists.txt @@ -8,6 +8,6 @@ if (APPLE) include(CMakeLists.darwin.txt) -elseif (UNIX AND NOT APPLE) +elseif (CMAKE_SYSTEM_PROCESSOR STREQUAL "x86_64" AND UNIX AND NOT APPLE) include(CMakeLists.linux.txt) endif() diff --git a/util/datetime/cputimer.cpp b/util/datetime/cputimer.cpp index a032dbd3df..32ccfd4740 100644 --- a/util/datetime/cputimer.cpp +++ b/util/datetime/cputimer.cpp @@ -49,10 +49,27 @@ TDuration CyclesToDuration(ui64 cycles) { return TDuration::MicroSeconds(cycles * 1000000 / GetCyclesPerSecond()); } +TDuration CyclesToDurationSafe(ui64 cycles) +{ + constexpr ui64 cyclesLimit = std::numeric_limits<ui64>::max() / 1000000; + if (cycles <= cyclesLimit) { + return CyclesToDuration(cycles); + } + return TDuration::MicroSeconds(cycles / GetCyclesPerSecond() * 1000000); +} + ui64 DurationToCycles(TDuration duration) { return duration.MicroSeconds() * GetCyclesPerSecond() / 1000000; } +ui64 DurationToCyclesSafe(TDuration duration) +{ + if (duration.MicroSeconds() <= std::numeric_limits<ui64>::max() / GetCyclesPerSecond()) { + return DurationToCycles(duration); + } + return duration.MicroSeconds() / 1000000 * GetCyclesPerSecond(); +} + TPrecisionTimer::TPrecisionTimer() : Start(::GetCycleCount()) { diff --git a/util/datetime/cputimer.h b/util/datetime/cputimer.h index 7d38d5bdb3..b24d6fae8e 100644 --- a/util/datetime/cputimer.h +++ b/util/datetime/cputimer.h @@ -62,6 +62,10 @@ void SetCyclesPerSecond(ui64 cycles); TDuration CyclesToDuration(ui64 cycles); ui64 DurationToCycles(TDuration duration); +// NBS-3400 - CyclesToDuration and DurationToCycles may overflow for long running events +TDuration CyclesToDurationSafe(ui64 cycles); +ui64 DurationToCyclesSafe(TDuration duration); + class TPrecisionTimer { private: ui64 Start = 0; diff --git a/util/datetime/cputimer_ut.cpp b/util/datetime/cputimer_ut.cpp new file mode 100644 index 0000000000..21a657d5c7 --- /dev/null +++ b/util/datetime/cputimer_ut.cpp @@ -0,0 +1,10 @@ +#include <library/cpp/testing/unittest/registar.h> + +#include "cputimer.h" + +Y_UNIT_TEST_SUITE(TestCpuTimerSuite) { + Y_UNIT_TEST(TestCyclesToDurationSafe) { + ui64 cycles = DurationToCyclesSafe(TDuration::Hours(24)); + UNIT_ASSERT_VALUES_EQUAL(24, CyclesToDurationSafe(cycles).Hours()); + } +} diff --git a/util/system/hostname.cpp b/util/system/hostname.cpp index 386f646d6b..e377910d5c 100644 --- a/util/system/hostname.cpp +++ b/util/system/hostname.cpp @@ -34,8 +34,6 @@ namespace { struct TFQDNHostNameHolder { inline TFQDNHostNameHolder() { - struct addrinfo hints; - struct addrinfo* ais{nullptr}; char buf[1024]; memset(buf, 0, sizeof(buf)); @@ -44,20 +42,41 @@ namespace { ythrow TSystemError() << "can not get hostname"; } +#ifdef _darwin_ + // On Darwin gethostname returns fqdn, see hostname.c in shell_cmds: + // https://github.com/apple-oss-distributions/shell_cmds/blob/main/hostname/hostname.c + // There are macs in the wild that don't have fqdn hostnames, but + // which have search domains in their resolv.conf, so any attempt to + // resolve AI_CANONNAME for the short hostname will result in the + // EAI_NONAME error. + // It seems using gethostname is enough to emulate the result of + // `hostname -f`, which still works on those macs. + FQDNHostName = buf; +#else + // On Linux `hostname -f` calls getaddrinfo with AI_CANONNAME flag + // to find the fqdn and will fail on any error. + // Hosts often have a short hostname and fqdn is resolved over dns. + // It is also very common to have a short hostname alias in + // /etc/hosts, which works as a fallback (e.g. no fqdn in search + // domains, otherwise `hostname -f` fails with an error and it is + // obvious the host is not configured correctly). + // Note that getaddrinfo may sometimes return EAI_NONAME even when + // host actually has fqdn, but dns is temporary unavailable, so we + // cannot ignore any errors on Linux. + struct addrinfo hints; + struct addrinfo* ais{nullptr}; + memset(&hints, 0, sizeof(hints)); hints.ai_family = AF_UNSPEC; hints.ai_flags = AI_CANONNAME; res = getaddrinfo(buf, nullptr, &hints, &ais); if (res) { - if (res != EAI_NONAME) { - ythrow TSystemError() << "can not get FQDN (return code is " << res << ", hostname is \"" << buf << "\")"; - } - FQDNHostName = buf; - } else { - FQDNHostName = ais->ai_canonname; - freeaddrinfo(ais); + ythrow TSystemError() << "can not get FQDN (return code is " << res << ", hostname is \"" << buf << "\")"; } + FQDNHostName = ais->ai_canonname; FQDNHostName.to_lower(); + freeaddrinfo(ais); +#endif } TString FQDNHostName; |