80 KiB
80 KiB
<html lang="en">
<head>
</head>
</html>
LCOV - code coverage report | ||||||||||||||||||||||
![]() | ||||||||||||||||||||||
|
||||||||||||||||||||||
![]() |
Line data Source code 1 : #ifndef C10_UTIL_EXCEPTION_H_ 2 : #define C10_UTIL_EXCEPTION_H_ 3 : 4 : #include <c10/macros/Macros.h> 5 : #include <c10/util/StringUtil.h> 6 : #include <c10/util/variant.h> 7 : 8 : #include <cstddef> 9 : #include <exception> 10 : #include <string> 11 : #include <vector> 12 : 13 : #if defined(_MSC_VER) && _MSC_VER <= 1900 14 : #define __func__ __FUNCTION__ 15 : #endif 16 : 17 : namespace c10 { 18 : 19 : /// The primary ATen error class. 20 : /// Provides a complete error message with source location information via 21 : /// `what()`, and a more concise message via `what_without_backtrace()`. 22 : /// Don't throw this directly; use TORCH_CHECK/TORCH_INTERNAL_ASSERT instead. 23 : /// 24 : /// NB: c10::Error is handled specially by the default torch to suppress the 25 : /// backtrace, see torch/csrc/Exceptions.h 26 : class C10_API Error : public std::exception { 27 : // The actual error message. 28 : std::string msg_; 29 : 30 : // Context for the message (in order of decreasing specificity). Context will 31 : // be automatically formatted appropriately, so it is not necessary to add 32 : // extra leading/trailing newlines to strings inside this vector 33 : std::vector<std::string> context_; 34 : 35 : // The C++ backtrace at the point when this exception was raised. This 36 : // may be empty if there is no valid backtrace. (We don't use optional 37 : // here to reduce the dependencies this file has.) 38 : std::string backtrace_; 39 : 40 : // These two are derived fields from msg_stack_ and backtrace_, but we need 41 : // fields for the strings so that we can return a const char* (as the 42 : // signature of std::exception requires). Currently, the invariant 43 : // is that these fields are ALWAYS populated consistently with respect 44 : // to msg_stack_ and backtrace_. 45 : std::string what_; 46 : std::string what_without_backtrace_; 47 : 48 : // This is a little debugging trick: you can stash a relevant pointer 49 : // in caller, and then when you catch the exception, you can compare 50 : // against pointers you have on hand to get more information about 51 : // where the exception came from. In Caffe2, this is used to figure 52 : // out which operator raised an exception. 53 : const void* caller_; 54 : 55 : public: 56 : // PyTorch-style Error constructor. NB: the implementation of this 57 : // is actually in Logging.cpp 58 : Error(SourceLocation source_location, std::string msg); 59 : 60 : // Caffe2-style error message 61 : Error( 62 : const char* file, 63 : const uint32_t line, 64 : const char* condition, 65 : const std::string& msg, 66 : const std::string& backtrace, 67 : const void* caller = nullptr); 68 : 69 : // Base constructor 70 : Error(std::string msg, std::string backtrace, const void* caller = nullptr); 71 : 72 : // Add some new context to the message stack. The last added context 73 : // will be formatted at the end of the context list upon printing. 74 : // WARNING: This method is O(n) in the size of the stack, so don't go 75 : // wild adding a ridiculous amount of context to error messages. 76 : void add_context(std::string msg); 77 : 78 : const std::string& msg() const { 79 : return msg_; 80 : } 81 : 82 : const std::vector<std::string>& context() const { 83 : return context_; 84 : } 85 : 86 : const std::string& backtrace() const { 87 : return backtrace_; 88 : } 89 : 90 : /// Returns the complete error message, including the source location. 91 : /// The returned pointer is invalidated if you call add_context() on 92 : /// this object. 93 0 : const char* what() const noexcept override { 94 0 : return what_.c_str(); 95 : } 96 : 97 : const void* caller() const noexcept { 98 : return caller_; 99 : } 100 : 101 : /// Returns only the error message string, without source location. 102 : /// The returned pointer is invalidated if you call add_context() on 103 : /// this object. 104 : const char* what_without_backtrace() const noexcept { 105 : return what_without_backtrace_.c_str(); 106 : } 107 : 108 : private: 109 : void refresh_what(); 110 : std::string compute_what(bool include_backtrace) const; 111 : }; 112 : 113 : class C10_API Warning { 114 : public: 115 : class C10_API UserWarning {}; 116 : class C10_API DeprecationWarning {}; 117 : 118 : using warning_variant_t = c10::variant<UserWarning, DeprecationWarning>; 119 : 120 : Warning( 121 : warning_variant_t type, 122 : const SourceLocation& source_location, 123 : std::string msg, 124 : bool verbatim); 125 : 126 : Warning( 127 : warning_variant_t type, 128 : SourceLocation source_location, 129 : const char* msg, 130 : bool verbatim); 131 : 132 : Warning( 133 : warning_variant_t type, 134 : SourceLocation source_location, 135 : ::c10::detail::CompileTimeEmptyString msg, 136 : bool verbatim); 137 : 138 : // Getters for members 139 : warning_variant_t type() const; 140 : const SourceLocation& source_location() const; 141 : const std::string& msg() const; 142 : bool verbatim() const; 143 : 144 : private: 145 : // The type of warning 146 : warning_variant_t type_; 147 : 148 : // Where the warning happened. 149 : SourceLocation source_location_; 150 : 151 : // The actual warning message. 152 : std::string msg_; 153 : 154 : // See note: [Verbatim Warnings] 155 : bool verbatim_; 156 : }; 157 : 158 : using UserWarning = Warning::UserWarning; 159 : using DeprecationWarning = Warning::DeprecationWarning; 160 : 161 : // Issue a warning with a given message. Dispatched to the current 162 : // warning handler. 163 : void C10_API warn(const Warning& warning); 164 : 165 : class C10_API WarningHandler { 166 : public: 167 : virtual ~WarningHandler() = default; 168 : /// The default warning handler. Prints the message to stderr. 169 : virtual void process(const Warning& warning); 170 : }; 171 : 172 : namespace WarningUtils { 173 : 174 : // Note: [Verbatim Warnings] 175 : // Warnings originating in C++ code can appear out-of-place to Python users: 176 : // a user runs a line in Python, but the warning references a line in C++. 177 : // Some parts of PyTorch, like the JIT, are cognizant of this mismatch 178 : // and take care to map warnings back to the user's program, but most 179 : // of PyTorch simply throws a context-free warning. To allow warning 180 : // handlers to add context where appropriate, warn takes the 181 : // "verbatim" flag. When this is false a warning handler might append 182 : // the C++ warning to a Python warning message that relates the warning 183 : // back to the user's program. Callers who have already accounted for 184 : // context in their warnings should set verbatim to true so their warnings 185 : // appear without modification. 186 : 187 : /// Sets the global warning handler. This is not thread-safe, so it should 188 : /// generally be called once during initialization or while holding the GIL 189 : /// for programs that use python. 190 : /// User is responsible for keeping the WarningHandler alive until 191 : /// it is not needed. 192 : C10_API void set_warning_handler(WarningHandler* handler) noexcept(true); 193 : /// Gets the global warning handler. 194 : C10_API WarningHandler* get_warning_handler() noexcept(true); 195 : 196 : class C10_API WarningHandlerGuard { 197 : WarningHandler* prev_handler_; 198 : 199 : public: 200 : WarningHandlerGuard(WarningHandler* new_handler) 201 : : prev_handler_(c10::WarningUtils::get_warning_handler()) { 202 : c10::WarningUtils::set_warning_handler(new_handler); 203 : } 204 : ~WarningHandlerGuard() { 205 : c10::WarningUtils::set_warning_handler(prev_handler_); 206 : } 207 : }; 208 : 209 : /// The TORCH_WARN_ONCE macro is difficult to test for. Use 210 : /// setWarnAlways(true) to turn it into TORCH_WARN, which can be 211 : /// tested for more easily. 212 : C10_API void set_warnAlways(bool) noexcept(true); 213 : C10_API bool get_warnAlways(void) noexcept(true); 214 : 215 : // A RAII guard that sets warn_always (not thread-local) on 216 : // construction, and sets it back to the original value upon destruction. 217 : struct C10_API WarnAlways { 218 : public: 219 : explicit WarnAlways(bool setting = true); 220 : ~WarnAlways(); 221 : 222 : private: 223 : bool prev_setting; 224 : }; 225 : 226 : } // namespace WarningUtils 227 : 228 : // Used in ATen for out-of-bound indices that can reasonably only be detected 229 : // lazily inside a kernel (See: advanced indexing). These turn into 230 : // IndexError when they cross to Python. 231 : class C10_API IndexError : public Error { 232 : using Error::Error; 233 : }; 234 : 235 : // Used in ATen for invalid values. These turn into 236 : // ValueError when they cross to Python. 237 : class C10_API ValueError : public Error { 238 : using Error::Error; 239 : }; 240 : 241 : // Used in ATen for invalid types. These turn into 242 : // TypeError when they cross to Python. 243 : class C10_API TypeError : public Error { 244 : using Error::Error; 245 : }; 246 : 247 : // Used in ATen for functionality that is not implemented. These turn into 248 : // NotImplementedError when they cross to Python. 249 : class C10_API NotImplementedError : public Error { 250 : using Error::Error; 251 : }; 252 : 253 : // Used in ATen for non finite indices. These turn into 254 : // ExitException when they cross to Python. 255 : class C10_API EnforceFiniteError : public Error { 256 : using Error::Error; 257 : }; 258 : 259 : // Used in Onnxifi backend lowering. These turn into 260 : // ExitException when they cross to Python. 261 : class C10_API OnnxfiBackendSystemError : public Error { 262 : using Error::Error; 263 : }; 264 : 265 : // Used for numerical errors from the linalg module. These 266 : // turn into LinAlgError when they cross into Python. 267 : class C10_API LinAlgError : public Error { 268 : using Error::Error; 269 : }; 270 : 271 : class C10_API OutOfMemoryError : public Error { 272 : using Error::Error; 273 : }; 274 : 275 : // Used for collective communication library errors from the distributed module. 276 : // These turn into DistBackendError when they cross into Python. 277 : class C10_API DistBackendError : public Error { 278 : using Error::Error; 279 : }; 280 : 281 : // A utility function to return an exception std::string by prepending its 282 : // exception type before its what() content 283 : C10_API std::string GetExceptionString(const std::exception& e); 284 : 285 : } // namespace c10 286 : 287 : // Private helper macro for implementing TORCH_INTERNAL_ASSERT and TORCH_CHECK 288 : // 289 : // Note: In the debug build With MSVC, __LINE__ might be of long type (a.k.a 290 : // int32_t), which is different from the definition of `SourceLocation` that 291 : // requires unsigned int (a.k.a uint32_t) and may cause a compile error with the 292 : // message: error C2397: conversion from 'long' to 'uint32_t' requires a 293 : // narrowing conversion Here the static cast is used to pass the build. if this 294 : // is used inside a lambda the __func__ macro expands to operator(), which isn't 295 : // very useful, but hard to fix in a macro so suppressing the warning. 296 : #define C10_THROW_ERROR(err_type, msg) \ 297 : throw ::c10::err_type( \ 298 : {__func__, __FILE__, static_cast<uint32_t>(__LINE__)}, msg) 299 : 300 : // Private helper macro for workaround MSVC misexpansion of nested macro 301 : // invocations involving __VA_ARGS__. See 302 : // https://stackoverflow.com/questions/5134523/msvc-doesnt-expand-va-args-correctly 303 : #define C10_EXPAND_MSVC_WORKAROUND(x) x 304 : 305 : // On nvcc, C10_UNLIKELY thwarts missing return statement analysis. In cases 306 : // where the unlikely expression may be a constant, use this macro to ensure 307 : // return statement analysis keeps working (at the cost of not getting the 308 : // likely/unlikely annotation on nvcc). 309 : // https://github.com/pytorch/pytorch/issues/21418 310 : // 311 : // Currently, this is only used in the error reporting macros below. If you 312 : // want to use it more generally, move me to Macros.h 313 : // 314 : // TODO: Brian Vaughan observed that we might be able to get this to work on 315 : // nvcc by writing some sort of C++ overload that distinguishes constexpr inputs 316 : // from non-constexpr. Since there isn't any evidence that losing C10_UNLIKELY 317 : // in nvcc is causing us perf problems, this is not yet implemented, but this 318 : // might be an interesting piece of C++ code for an intrepid bootcamper to 319 : // write. 320 : #if defined(__CUDACC__) 321 : #define C10_UNLIKELY_OR_CONST(e) e 322 : #else 323 : #define C10_UNLIKELY_OR_CONST(e) C10_UNLIKELY(e) 324 : #endif 325 : 326 : // ---------------------------------------------------------------------------- 327 : // Error reporting macros 328 : // ---------------------------------------------------------------------------- 329 : 330 : #ifdef STRIP_ERROR_MESSAGES 331 : #define TORCH_RETHROW(e, ...) throw 332 : #else 333 : #define TORCH_RETHROW(e, ...) \ 334 : do { \ 335 : e.add_context(::c10::str(__VA_ARGS__)); \ 336 : throw; \ 337 : } while (false) 338 : #endif 339 : 340 : // A utility macro to provide assert()-like functionality; that is, enforcement 341 : // of internal invariants in code. It supports an arbitrary number of extra 342 : // arguments (evaluated only on failure), which will be printed in the assert 343 : // failure message using operator<< (this is useful to print some variables 344 : // which may be useful for debugging.) 345 : // 346 : // Usage: 347 : // TORCH_INTERNAL_ASSERT(should_be_true); 348 : // TORCH_INTERNAL_ASSERT(x == 0, "x = ", x); 349 : // 350 : // Assuming no bugs in PyTorch, the conditions tested by this macro should 351 : // always be true; e.g., it should be possible to disable all of these 352 : // conditions without changing observable user behavior. If you would like to 353 : // do error reporting for user input, please use TORCH_CHECK instead. 354 : // 355 : // NOTE: It is SAFE to use this macro in production code; on failure, this 356 : // simply raises an exception, it does NOT unceremoniously quit the process 357 : // (unlike assert()). 358 : // 359 : #ifdef STRIP_ERROR_MESSAGES 360 : #define TORCH_INTERNAL_ASSERT(cond, ...) \ 361 : if (C10_UNLIKELY_OR_CONST(!(cond))) { \ 362 : ::c10::detail::torchCheckFail( \ 363 : __func__, \ 364 : __FILE__, \ 365 : static_cast<uint32_t>(__LINE__), \ 366 : #cond " INTERNAL ASSERT FAILED at " C10_STRINGIZE(__FILE__)); \ 367 : } 368 : #else 369 : // It would be nice if we could build a combined string literal out of 370 : // the TORCH_INTERNAL_ASSERT prefix and a user-provided string literal 371 : // as the first argument, but there doesn't seem to be any good way to 372 : // do that while still supporting having a first argument that isn't a 373 : // string literal. 374 : #define TORCH_INTERNAL_ASSERT(cond, ...) \ 375 : if (C10_UNLIKELY_OR_CONST(!(cond))) { \ 376 : ::c10::detail::torchInternalAssertFail( \ 377 : __func__, \ 378 : __FILE__, \ 379 : static_cast<uint32_t>(__LINE__), \ 380 : #cond \ 381 : " INTERNAL ASSERT FAILED at " C10_STRINGIZE(__FILE__) ":" C10_STRINGIZE( \ 382 : __LINE__) ", please report a bug to PyTorch. ", \ 383 : c10::str(__VA_ARGS__)); \ 384 : } 385 : #endif 386 : 387 : // A utility macro to make it easier to test for error conditions from user 388 : // input. Like TORCH_INTERNAL_ASSERT, it supports an arbitrary number of extra 389 : // arguments (evaluated only on failure), which will be printed in the error 390 : // message using operator<< (e.g., you can pass any object which has 391 : // operator<< defined. Most objects in PyTorch have these definitions!) 392 : // 393 : // Usage: 394 : // TORCH_CHECK(should_be_true); // A default error message will be provided 395 : // // in this case; but we recommend writing an 396 : // // explicit error message, as it is more 397 : // // user friendly. 398 : // TORCH_CHECK(x == 0, "Expected x to be 0, but got ", x); 399 : // 400 : // On failure, this macro will raise an exception. If this exception propagates 401 : // to Python, it will convert into a Python RuntimeError. 402 : // 403 : // NOTE: It is SAFE to use this macro in production code; on failure, this 404 : // simply raises an exception, it does NOT unceremoniously quit the process 405 : // (unlike CHECK() from glog.) 406 : // 407 : #define TORCH_CHECK_WITH(error_t, cond, ...) \ 408 : TORCH_CHECK_WITH_MSG(error_t, cond, "", __VA_ARGS__) 409 : 410 : #ifdef STRIP_ERROR_MESSAGES 411 : #define TORCH_CHECK_MSG(cond, type, ...) \ 412 : (#cond #type " CHECK FAILED at " C10_STRINGIZE(__FILE__)) 413 : #define TORCH_CHECK_WITH_MSG(error_t, cond, type, ...) \ 414 : if (C10_UNLIKELY_OR_CONST(!(cond))) { \ 415 : C10_THROW_ERROR(Error, TORCH_CHECK_MSG(cond, type, __VA_ARGS__)); \ 416 : } 417 : #else 418 : namespace c10 { 419 : namespace detail { 420 : template <typename... Args> 421 0 : decltype(auto) torchCheckMsgImpl(const char* /*msg*/, const Args&... args) { 422 0 : return ::c10::str(args...); 423 : } 424 0 : inline C10_API const char* torchCheckMsgImpl(const char* msg) { 425 0 : return msg; 426 : } 427 : // If there is just 1 user-provided C-string argument, use it. 428 0 : inline C10_API const char* torchCheckMsgImpl( 429 : const char* /*msg*/, 430 : const char* args) { 431 0 : return args; 432 : } 433 : } // namespace detail 434 : } // namespace c10 435 : 436 : #define TORCH_CHECK_MSG(cond, type, ...) \ 437 : (::c10::detail::torchCheckMsgImpl( \ 438 : "Expected " #cond \ 439 : " to be true, but got false. " \ 440 : "(Could this error message be improved? If so, " \ 441 : "please report an enhancement request to PyTorch.)", \ 442 : ##__VA_ARGS__)) 443 : #define TORCH_CHECK_WITH_MSG(error_t, cond, type, ...) \ 444 : if (C10_UNLIKELY_OR_CONST(!(cond))) { \ 445 : C10_THROW_ERROR(error_t, TORCH_CHECK_MSG(cond, type, __VA_ARGS__)); \ 446 : } 447 : #endif 448 : 449 : namespace c10 { 450 : namespace detail { 451 : 452 : [[noreturn]] C10_API void torchCheckFail( 453 : const char* func, 454 : const char* file, 455 : uint32_t line, 456 : const std::string& msg); 457 : [[noreturn]] C10_API void torchCheckFail( 458 : const char* func, 459 : const char* file, 460 : uint32_t line, 461 : const char* msg); 462 : 463 : // The c10::str() call that creates userMsg can have 1 of 3 return 464 : // types depending on the number and types of arguments passed to 465 : // TORCH_INTERNAL_ASSERT. 0 arguments will get a 466 : // CompileTimeEmptyString, 1 const char * will be passed straight 467 : // through, and anything else will get converted to std::string. 468 : [[noreturn]] C10_API void torchInternalAssertFail( 469 : const char* func, 470 : const char* file, 471 : uint32_t line, 472 : const char* condMsg, 473 : const char* userMsg); 474 0 : [[noreturn]] inline C10_API void torchInternalAssertFail( 475 : const char* func, 476 : const char* file, 477 : uint32_t line, 478 : const char* condMsg, 479 : ::c10::detail::CompileTimeEmptyString /*userMsg*/) { 480 0 : torchCheckFail(func, file, line, condMsg); 481 : } 482 : [[noreturn]] C10_API void torchInternalAssertFail( 483 : const char* func, 484 : const char* file, 485 : uint32_t line, 486 : const char* condMsg, 487 : const std::string& userMsg); 488 : 489 : } // namespace detail 490 : } // namespace c10 491 : 492 : #ifdef STRIP_ERROR_MESSAGES 493 : #define TORCH_CHECK(cond, ...) \ 494 : if (C10_UNLIKELY_OR_CONST(!(cond))) { \ 495 : ::c10::detail::torchCheckFail( \ 496 : __func__, \ 497 : __FILE__, \ 498 : static_cast<uint32_t>(__LINE__), \ 499 : TORCH_CHECK_MSG(cond, "", __VA_ARGS__)); \ 500 : } 501 : #else 502 : #define TORCH_CHECK(cond, ...) \ 503 : if (C10_UNLIKELY_OR_CONST(!(cond))) { \ 504 : ::c10::detail::torchCheckFail( \ 505 : __func__, \ 506 : __FILE__, \ 507 : static_cast<uint32_t>(__LINE__), \ 508 : TORCH_CHECK_MSG(cond, "", ##__VA_ARGS__)); \ 509 : } 510 : #endif 511 : 512 : // An utility macro that does what `TORCH_CHECK` does if compiled in the host 513 : // code, otherwise does nothing. Supposed to be used in the code shared between 514 : // host and device code as an alternative for `TORCH_CHECK`. 515 : #if defined(__CUDACC__) || defined(__HIPCC__) 516 : #define TORCH_CHECK_IF_NOT_ON_CUDA(cond, ...) 517 : #else 518 : #define TORCH_CHECK_IF_NOT_ON_CUDA(cond, ...) TORCH_CHECK(cond, ##__VA_ARGS__) 519 : #endif 520 : 521 : // Debug only version of TORCH_INTERNAL_ASSERT. This macro only checks in debug 522 : // build, and does nothing in release build. It is appropriate to use 523 : // in situations where you want to add an assert to a hotpath, but it is 524 : // too expensive to run this assert on production builds. 525 : #ifdef NDEBUG 526 : // Optimized version - generates no code. 527 : #define TORCH_INTERNAL_ASSERT_DEBUG_ONLY(...) \ 528 : while (false) \ 529 : C10_EXPAND_MSVC_WORKAROUND(TORCH_INTERNAL_ASSERT(__VA_ARGS__)) 530 : #else 531 : #define TORCH_INTERNAL_ASSERT_DEBUG_ONLY(...) \ 532 : C10_EXPAND_MSVC_WORKAROUND(TORCH_INTERNAL_ASSERT(__VA_ARGS__)) 533 : #endif 534 : 535 : // TODO: We're going to get a lot of similar looking string literals 536 : // this way; check if this actually affects binary size. 537 : 538 : // Like TORCH_CHECK, but raises LinAlgError instead of Error. 539 : #define TORCH_CHECK_LINALG(cond, ...) \ 540 : TORCH_CHECK_WITH_MSG(LinAlgError, cond, "LINALG", __VA_ARGS__) 541 : 542 : // Like TORCH_CHECK, but raises IndexErrors instead of Errors. 543 : #define TORCH_CHECK_INDEX(cond, ...) \ 544 : TORCH_CHECK_WITH_MSG(IndexError, cond, "INDEX", __VA_ARGS__) 545 : 546 : // Like TORCH_CHECK, but raises ValueErrors instead of Errors. 547 : #define TORCH_CHECK_VALUE(cond, ...) \ 548 : TORCH_CHECK_WITH_MSG(ValueError, cond, "VALUE", __VA_ARGS__) 549 : 550 : // Like TORCH_CHECK, but raises TypeErrors instead of Errors. 551 : #define TORCH_CHECK_TYPE(cond, ...) \ 552 : TORCH_CHECK_WITH_MSG(TypeError, cond, "TYPE", __VA_ARGS__) 553 : 554 : // Like TORCH_CHECK, but raises NotImplementedErrors instead of Errors. 555 : #define TORCH_CHECK_NOT_IMPLEMENTED(cond, ...) \ 556 : TORCH_CHECK_WITH_MSG(NotImplementedError, cond, "TYPE", __VA_ARGS__) 557 : 558 : #ifdef STRIP_ERROR_MESSAGES 559 : #define WARNING_MESSAGE_STRING(...) \ 560 : ::c10::detail::CompileTimeEmptyString {} 561 : #else 562 : #define WARNING_MESSAGE_STRING(...) ::c10::str(__VA_ARGS__) 563 : #endif 564 : 565 : // Report a warning to the user. Accepts an arbitrary number of extra 566 : // arguments which are concatenated into the warning message using operator<< 567 : // 568 : #ifdef DISABLE_WARN 569 : #define _TORCH_WARN_WITH(...) ((void)0); 570 : #else 571 : #define _TORCH_WARN_WITH(warning_t, ...) \ 572 : ::c10::warn(::c10::Warning( \ 573 : warning_t(), \ 574 : {__func__, __FILE__, static_cast<uint32_t>(__LINE__)}, \ 575 : WARNING_MESSAGE_STRING(__VA_ARGS__), \ 576 : false)); 577 : #endif 578 : 579 : #define TORCH_WARN(...) _TORCH_WARN_WITH(::c10::UserWarning, __VA_ARGS__); 580 : 581 : #define TORCH_WARN_DEPRECATION(...) \ 582 : _TORCH_WARN_WITH(::c10::DeprecationWarning, __VA_ARGS__); 583 : 584 : // Report a warning to the user only once. Accepts an arbitrary number of extra 585 : // arguments which are concatenated into the warning message using operator<< 586 : // 587 : #define _TORCH_WARN_ONCE(...) \ 588 : C10_UNUSED static const auto C10_ANONYMOUS_VARIABLE(torch_warn_once_) = \ 589 : [&] { \ 590 : TORCH_WARN(__VA_ARGS__); \ 591 : return true; \ 592 : }() 593 : 594 : #ifdef DISABLE_WARN 595 : #define TORCH_WARN_ONCE(...) ((void)0); 596 : #else 597 : #define TORCH_WARN_ONCE(...) \ 598 : if (::c10::WarningUtils::get_warnAlways()) { \ 599 : TORCH_WARN(__VA_ARGS__); \ 600 : } else { \ 601 : _TORCH_WARN_ONCE(__VA_ARGS__); \ 602 : } 603 : #endif 604 : 605 : // Report an error with a specific argument 606 : // NOTE: using the argument name in TORCH_CHECK's message is preferred 607 : #define TORCH_CHECK_ARG(cond, argN, ...) \ 608 : TORCH_CHECK(cond, "invalid argument ", argN, ": ", __VA_ARGS__) 609 : 610 : // ---------------------------------------------------------------------------- 611 : // Deprecated macros 612 : // ---------------------------------------------------------------------------- 613 : 614 : namespace c10 { 615 : namespace detail { 616 : 617 : /* 618 : // Deprecation disabled until we fix sites in our codebase 619 : C10_DEPRECATED_MESSAGE("AT_ERROR(msg) is deprecated, use TORCH_CHECK(false, msg) 620 : instead.") 621 : */ 622 : inline void deprecated_AT_ERROR() {} 623 : 624 : /* 625 : // Deprecation disabled until we fix sites in our codebase 626 : C10_DEPRECATED_MESSAGE("AT_ASSERT is deprecated, if you mean to indicate an 627 : internal invariant failure, use " \ 628 : "TORCH_INTERNAL_ASSERT instead; if you mean to do user 629 : error checking, use " \ "TORCH_CHECK. See 630 : https://github.com/pytorch/pytorch/issues/20287 for more details.") 631 : */ 632 0 : inline void deprecated_AT_ASSERT() {} 633 : 634 : /* 635 : // Deprecation disabled until we fix sites in our codebase 636 : C10_DEPRECATED_MESSAGE("AT_ASSERTM is deprecated, if you mean to indicate an 637 : internal invariant failure, use " \ 638 : "TORCH_INTERNAL_ASSERT instead; if you mean to do user 639 : error checking, use " \ "TORCH_CHECK. See 640 : https://github.com/pytorch/pytorch/issues/20287 for more details.") 641 : */ 642 : inline void deprecated_AT_ASSERTM() {} 643 : 644 : } // namespace detail 645 : } // namespace c10 646 : 647 : // Deprecated alias; this alias was deprecated because people kept mistakenly 648 : // using it for user error checking. Use TORCH_INTERNAL_ASSERT or TORCH_CHECK 649 : // instead. See https://github.com/pytorch/pytorch/issues/20287 for more 650 : // details. 651 : #define AT_ASSERT(...) \ 652 : do { \ 653 : ::c10::detail::deprecated_AT_ASSERT(); \ 654 : C10_EXPAND_MSVC_WORKAROUND(TORCH_INTERNAL_ASSERT(__VA_ARGS__)); \ 655 : } while (false) 656 : 657 : // Deprecated alias, like AT_ASSERT. The new TORCH_INTERNAL_ASSERT macro 658 : // supports both 0-ary and variadic calls, so having a separate 659 : // message-accepting macro is not necessary. 660 : // 661 : // NB: we MUST include cond explicitly here, as MSVC will miscompile the macro 662 : // expansion, shunting all of __VA_ARGS__ to cond. An alternate workaround 663 : // can be seen at 664 : // https://stackoverflow.com/questions/5134523/msvc-doesnt-expand-va-args-correctly 665 : #define AT_ASSERTM(cond, ...) \ 666 : do { \ 667 : ::c10::detail::deprecated_AT_ASSERTM(); \ 668 : C10_EXPAND_MSVC_WORKAROUND(TORCH_INTERNAL_ASSERT(cond, __VA_ARGS__)); \ 669 : } while (false) 670 : 671 : // Deprecated alias; this alias was deprecated because it represents extra API 672 : // surface that makes it hard for people to understand what macro to use. 673 : // Use TORCH_CHECK(false, ...) or TORCH_INTERNAL_ASSERT(false, ...) to 674 : // unconditionally fail at a line of code. 675 : #define AT_ERROR(...) \ 676 : do { \ 677 : ::c10::detail::deprecated_AT_ERROR(); \ 678 : C10_EXPAND_MSVC_WORKAROUND(TORCH_CHECK(false, ::c10::str(__VA_ARGS__))); \ 679 : } while (false) 680 : 681 : #endif // C10_UTIL_EXCEPTION_H_ |
![]() |
Generated by: LCOV version 2.0-1 |
</html>