From 510ee0ab4f09c6b0a8548aeb99c83ac11b143411 Mon Sep 17 00:00:00 2001 From: Niels Lohmann Date: Wed, 21 Oct 2026 18:45:37 +0200 Subject: [PATCH] Let the json_view error replay handler return from parse_error() sax_parse() recovers from an error if parse_error() returns true. For a handler whose parse_error() is [[noreturn]], MSVC reports that code as unreachable (C4702), which fails the /WX module build. throwing_sax now throws under a flag, as json_sax_dom_parser does. Signed-off-by: Niels Lohmann --- include/nlohmann/detail/view/errors.hpp | 14 ++++++++++++-- single_include/nlohmann/json_view.hpp | 14 ++++++++++++-- 2 files changed, 24 insertions(+), 4 deletions(-) diff --git a/include/nlohmann/detail/view/errors.hpp b/include/nlohmann/detail/view/errors.hpp index ca790a13d..1a2542ab3 100644 --- a/include/nlohmann/detail/view/errors.hpp +++ b/include/nlohmann/detail/view/errors.hpp @@ -124,11 +124,21 @@ struct throwing_sax /// (a template, as in json_sax_dom_parser: the parser passes the concrete /// exception type, which is thrown as is) + /// + /// It is not [[noreturn]]: sax_parse() recovers from an error if + /// parse_error() returns true, and MSVC reports that code as unreachable + /// (C4702) for a handler that never returns. The flag hides that from it. template - [[noreturn]] bool parse_error(std::size_t /*unused*/, const std::string& /*unused*/, const Exception& ex) + bool parse_error(std::size_t /*unused*/, const std::string& /*unused*/, const Exception& ex) { - NLOHMANN_VIEW_THROW(ex); + if (throwing) + { + NLOHMANN_VIEW_THROW(ex); + } + return false; // LCOV_EXCL_LINE } + + bool throwing = true; }; /*! diff --git a/single_include/nlohmann/json_view.hpp b/single_include/nlohmann/json_view.hpp index dfefa2633..b6f0859c3 100644 --- a/single_include/nlohmann/json_view.hpp +++ b/single_include/nlohmann/json_view.hpp @@ -2768,11 +2768,21 @@ struct throwing_sax /// (a template, as in json_sax_dom_parser: the parser passes the concrete /// exception type, which is thrown as is) + /// + /// It is not [[noreturn]]: sax_parse() recovers from an error if + /// parse_error() returns true, and MSVC reports that code as unreachable + /// (C4702) for a handler that never returns. The flag hides that from it. template - [[noreturn]] bool parse_error(std::size_t /*unused*/, const std::string& /*unused*/, const Exception& ex) + bool parse_error(std::size_t /*unused*/, const std::string& /*unused*/, const Exception& ex) { - NLOHMANN_VIEW_THROW(ex); + if (throwing) + { + NLOHMANN_VIEW_THROW(ex); + } + return false; // LCOV_EXCL_LINE } + + bool throwing = true; }; /*!