summaryrefslogtreecommitdiffstats
path: root/library/cpp
diff options
context:
space:
mode:
authorpechatnov <[email protected]>2025-08-06 18:42:10 +0300
committerpechatnov <[email protected]>2025-08-06 19:03:46 +0300
commit7bed48dd832fd169b9f9e4b820146228c934734b (patch)
treef51a6b2ec3d5a7be749b637c75c2346a56c04bf2 /library/cpp
parenta7b92fa6aa8979ff6da2ae0b16c1e3d79c04b95e (diff)
Optional description argument for YT_VERIFY, YT_ASSERT and others
commit_hash:80b47f95a2ee356b086f5955f2529f1b0e636db1
Diffstat (limited to 'library/cpp')
-rw-r--r--library/cpp/yt/assert/assert.cpp7
-rw-r--r--library/cpp/yt/assert/assert.h45
-rw-r--r--library/cpp/yt/assert/unittests/assert_ut.cpp98
-rw-r--r--library/cpp/yt/assert/unittests/ya.make13
-rw-r--r--library/cpp/yt/assert/ya.make4
5 files changed, 152 insertions, 15 deletions
diff --git a/library/cpp/yt/assert/assert.cpp b/library/cpp/yt/assert/assert.cpp
index 095357cdfa8..2329a5118db 100644
--- a/library/cpp/yt/assert/assert.cpp
+++ b/library/cpp/yt/assert/assert.cpp
@@ -10,6 +10,7 @@ namespace NYT::NDetail {
Y_WEAK void AssertTrapImpl(
TStringBuf trapType,
TStringBuf expr,
+ TStringBuf description,
TStringBuf file,
int line,
TStringBuf function)
@@ -20,8 +21,10 @@ Y_WEAK void AssertTrapImpl(
line,
function.data(),
expr.data(),
- "%s",
- trapType.data());
+ "%s: %.*s",
+ trapType.data(),
+ static_cast<int>(std::min<ui64>(description.length(), std::numeric_limits<int>::max())),
+ description.data());
}
////////////////////////////////////////////////////////////////////////////////
diff --git a/library/cpp/yt/assert/assert.h b/library/cpp/yt/assert/assert.h
index f2131d5bbcd..6430f136ffc 100644
--- a/library/cpp/yt/assert/assert.h
+++ b/library/cpp/yt/assert/assert.h
@@ -15,6 +15,7 @@ namespace NDetail {
void AssertTrapImpl(
TStringBuf trapType,
TStringBuf expr,
+ TStringBuf description,
TStringBuf file,
int line,
TStringBuf function);
@@ -27,31 +28,47 @@ void AssertTrapImpl(
#define YT_BUILTIN_TRAP() std::terminate()
#endif
-#define YT_ASSERT_TRAP(trapType, expr) \
- ::NYT::NDetail::AssertTrapImpl(TStringBuf(trapType), TStringBuf(expr), __SOURCE_FILE_IMPL__.As<TStringBuf>(), __LINE__, TStringBuf(__FUNCTION__)); \
- Y_UNREACHABLE() \
+#define YT_ASSERT_TRAP_IMPL(trapType, expr, description) \
+ ::NYT::NDetail::AssertTrapImpl( \
+ TStringBuf(trapType), \
+ TStringBuf(expr), \
+ TStringBuf(description), \
+ __SOURCE_FILE_IMPL__.As<TStringBuf>(), \
+ __LINE__, \
+ TStringBuf(__FUNCTION__)); \
+ Y_UNREACHABLE()
+#define YT_ASSERT_TRAP_IMPL_EXTRA_ARG(trapType, expr, description, _) YT_ASSERT_TRAP_IMPL(trapType, expr, description)
+
+#define YT_ASSERT_TRAP(trapType, expr, ...) \
+ YT_ASSERT_TRAP_IMPL##__VA_OPT__(_EXTRA_ARG)(trapType, expr, __VA_OPT__(__VA_ARGS__,) "")
+
+//! If |expr| is evaluated to false, abnormally terminates the current process in debug mode.
+//! Does nothing in release mode.
+//! Accepts an optional string argument that will be printed in error with #expr.
#ifdef NDEBUG
- #define YT_ASSERT(expr) \
+ #define YT_ASSERT(expr, ...) \
do { \
if (false) { \
(void) (expr); \
+ __VA_OPT__((void)(__VA_ARGS__)); \
} \
} while (false)
#else
- #define YT_ASSERT(expr) \
+ #define YT_ASSERT(expr, ...) \
do { \
if (Y_UNLIKELY(!(expr))) { \
- YT_ASSERT_TRAP("YT_ASSERT", #expr); \
+ YT_ASSERT_TRAP("YT_ASSERT", #expr __VA_OPT__(, __VA_ARGS__)); \
} \
} while (false)
#endif
//! Same as |YT_ASSERT| but evaluates and checks the expression in both release and debug mode.
-#define YT_VERIFY(expr) \
+//! Accepts an optional string argument that will be printed in error message with #expr.
+#define YT_VERIFY(expr, ...) \
do { \
if (Y_UNLIKELY(!(expr))) { \
- YT_ASSERT_TRAP("YT_VERIFY", #expr); \
+ YT_ASSERT_TRAP("YT_VERIFY", #expr __VA_OPT__(, __VA_ARGS__)); \
} \
} while (false)
@@ -70,19 +87,21 @@ void AssertTrapImpl(
#endif
//! Fatal error code marker. Abnormally terminates the current process.
+//! Accepts an optional string argument that will be printed in error message.
#ifdef YT_COMPILING_UDF
- #define YT_ABORT() __YT_BUILTIN_ABORT()
+ #define YT_ABORT(...) __YT_BUILTIN_ABORT()
#else
- #define YT_ABORT() \
+ #define YT_ABORT(...) \
do { \
- YT_ASSERT_TRAP("YT_ABORT", ""); \
+ YT_ASSERT_TRAP("YT_ABORT", "" __VA_OPT__(, __VA_ARGS__)); \
} while (false)
#endif
//! Unimplemented code marker. Abnormally terminates the current process.
-#define YT_UNIMPLEMENTED() \
+//! Accepts an optional string argument that will be printed in error message.
+#define YT_UNIMPLEMENTED(...) \
do { \
- YT_ASSERT_TRAP("YT_UNIMPLEMENTED", ""); \
+ YT_ASSERT_TRAP("YT_UNIMPLEMENTED", "" __VA_OPT__(, __VA_ARGS__)); \
} while (false)
////////////////////////////////////////////////////////////////////////////////
diff --git a/library/cpp/yt/assert/unittests/assert_ut.cpp b/library/cpp/yt/assert/unittests/assert_ut.cpp
new file mode 100644
index 00000000000..102f82618b1
--- /dev/null
+++ b/library/cpp/yt/assert/unittests/assert_ut.cpp
@@ -0,0 +1,98 @@
+#include <yt/yt/core/test_framework/framework.h>
+
+#include <library/cpp/yt/assert/assert.h>
+
+namespace NYT {
+namespace {
+
+////////////////////////////////////////////////////////////////////////////////
+
+TEST(TAssertTest, Abort)
+{
+ EXPECT_DEATH(
+ {
+ YT_ABORT();
+ },
+ "YT_ABORT");
+
+ EXPECT_DEATH(
+ {
+ YT_ABORT("MY_PROBLEM");
+ },
+ "MY_PROBLEM");
+}
+
+TEST(TAssertTest, Verify)
+{
+ YT_VERIFY(true);
+ YT_VERIFY(true, "12345");
+ YT_VERIFY(true, [] {
+ YT_ABORT();
+ return "NEVER_PRINTED";
+ } ());
+ EXPECT_DEATH(
+ {
+ YT_VERIFY(false);
+ },
+ "YT_VERIFY");
+ EXPECT_DEATH(
+ {
+ YT_VERIFY(false, "MY_MESSAGE");
+ },
+ "YT_VERIFY.*MY_MESSAGE");
+ EXPECT_DEATH(
+ {
+ YT_VERIFY(false && "my_specific_expression_part", "MY_MESSAGE");
+ },
+ "false && \"my_specific_expression_part\"");
+}
+
+TEST(TAssertTest, Assert)
+{
+ YT_ASSERT(true);
+ YT_ASSERT(true, [] {
+ YT_ABORT();
+ return "NEVER_PRINTED";
+ } ());
+ #ifndef NDEBUG
+ EXPECT_DEATH(
+ {
+ YT_ASSERT(false);
+ },
+ "YT_ASSERT");
+ EXPECT_DEATH(
+ {
+ YT_ASSERT(false, "MY_MESSAGE");
+ },
+ "MY_MESSAGE");
+ EXPECT_DEATH(
+ {
+ YT_ASSERT(false && "my_specific_expression_part", "MY_MESSAGE");
+ },
+ "my_specific_expression_part");
+ #endif
+}
+
+TEST(TAssertTest, Unimplemented)
+{
+ EXPECT_DEATH(
+ {
+ YT_UNIMPLEMENTED();
+ },
+ "YT_UNIMPLEMENTED");
+}
+
+TEST(TAssertTest, AcceptString)
+{
+ EXPECT_DEATH(
+ {
+ YT_ABORT(std::string("MY_PROBLEM"));
+ },
+ "MY_PROBLEM");
+}
+
+
+////////////////////////////////////////////////////////////////////////////////
+
+} // namespace
+} // namespace NYT
diff --git a/library/cpp/yt/assert/unittests/ya.make b/library/cpp/yt/assert/unittests/ya.make
new file mode 100644
index 00000000000..01e9479f4cd
--- /dev/null
+++ b/library/cpp/yt/assert/unittests/ya.make
@@ -0,0 +1,13 @@
+GTEST()
+
+INCLUDE(${ARCADIA_ROOT}/library/cpp/yt/ya_cpp.make.inc)
+
+PEERDIR(
+ library/cpp/yt/assert
+)
+
+SRCS(
+ assert_ut.cpp
+)
+
+END()
diff --git a/library/cpp/yt/assert/ya.make b/library/cpp/yt/assert/ya.make
index a9833ab70e9..4754d1d39a5 100644
--- a/library/cpp/yt/assert/ya.make
+++ b/library/cpp/yt/assert/ya.make
@@ -7,3 +7,7 @@ SRCS(
)
END()
+
+RECURSE_FOR_TESTS(
+ unittests
+)