| 1 | // Copyright Kevlin Henney, 2000-2005. |
| 2 | // Copyright Alexander Nasonov, 2006-2010. |
| 3 | // Copyright Antony Polukhin, 2011-2014. |
| 4 | // |
| 5 | // Distributed under the Boost Software License, Version 1.0. (See |
| 6 | // accompanying file LICENSE_1_0.txt or copy at |
| 7 | // http://www.boost.org/LICENSE_1_0.txt) |
| 8 | // |
| 9 | // what: lexical_cast custom keyword cast |
| 10 | // who: contributed by Kevlin Henney, |
| 11 | // enhanced with contributions from Terje Slettebo, |
| 12 | // with additional fixes and suggestions from Gennaro Prota, |
| 13 | // Beman Dawes, Dave Abrahams, Daryle Walker, Peter Dimov, |
| 14 | // Alexander Nasonov, Antony Polukhin, Justin Viiret, Michael Hofmann, |
| 15 | // Cheng Yang, Matthew Bradbury, David W. Birdsall, Pavel Korzh and other Boosters |
| 16 | // when: November 2000, March 2003, June 2005, June 2006, March 2011 - 2014 |
| 17 | |
| 18 | #ifndef BOOST_LEXICAL_CAST_BAD_LEXICAL_CAST_HPP |
| 19 | #define BOOST_LEXICAL_CAST_BAD_LEXICAL_CAST_HPP |
| 20 | |
| 21 | #include <boost/config.hpp> |
| 22 | #ifdef BOOST_HAS_PRAGMA_ONCE |
| 23 | # pragma once |
| 24 | #endif |
| 25 | |
| 26 | #include <typeinfo> |
| 27 | #include <exception> |
| 28 | #include <boost/throw_exception.hpp> |
| 29 | |
| 30 | namespace boost |
| 31 | { |
| 32 | // exception used to indicate runtime lexical_cast failure |
| 33 | class BOOST_SYMBOL_VISIBLE bad_lexical_cast : |
| 34 | // workaround MSVC bug with std::bad_cast when _HAS_EXCEPTIONS == 0 |
| 35 | #if defined(BOOST_MSVC) && defined(_HAS_EXCEPTIONS) && !_HAS_EXCEPTIONS |
| 36 | public std::exception |
| 37 | #else |
| 38 | public std::bad_cast |
| 39 | #endif |
| 40 | |
| 41 | #if defined(__BORLANDC__) && BOOST_WORKAROUND( __BORLANDC__, < 0x560 ) |
| 42 | // under bcc32 5.5.1 bad_cast doesn't derive from exception |
| 43 | , public std::exception |
| 44 | #endif |
| 45 | |
| 46 | { |
| 47 | public: |
| 48 | bad_lexical_cast() BOOST_NOEXCEPT |
| 49 | #ifndef BOOST_NO_TYPEID |
| 50 | : source(&typeid(void)), target(&typeid(void)) |
| 51 | #endif |
| 52 | {} |
| 53 | |
| 54 | virtual const char *what() const BOOST_NOEXCEPT_OR_NOTHROW { |
| 55 | return "bad lexical cast: " |
| 56 | "source type value could not be interpreted as target" ; |
| 57 | } |
| 58 | |
| 59 | virtual ~bad_lexical_cast() BOOST_NOEXCEPT_OR_NOTHROW |
| 60 | {} |
| 61 | |
| 62 | #ifndef BOOST_NO_TYPEID |
| 63 | bad_lexical_cast( |
| 64 | const std::type_info &source_type_arg, |
| 65 | const std::type_info &target_type_arg) BOOST_NOEXCEPT |
| 66 | : source(&source_type_arg), target(&target_type_arg) |
| 67 | {} |
| 68 | |
| 69 | const std::type_info &source_type() const BOOST_NOEXCEPT { |
| 70 | return *source; |
| 71 | } |
| 72 | |
| 73 | const std::type_info &target_type() const BOOST_NOEXCEPT { |
| 74 | return *target; |
| 75 | } |
| 76 | |
| 77 | private: |
| 78 | const std::type_info *source; |
| 79 | const std::type_info *target; |
| 80 | #endif |
| 81 | }; |
| 82 | |
| 83 | namespace conversion { namespace detail { |
| 84 | #ifdef BOOST_NO_TYPEID |
| 85 | template <class S, class T> |
| 86 | inline void throw_bad_cast() { |
| 87 | boost::throw_exception(bad_lexical_cast()); |
| 88 | } |
| 89 | #else |
| 90 | template <class S, class T> |
| 91 | inline void throw_bad_cast() { |
| 92 | boost::throw_exception(bad_lexical_cast(typeid(S), typeid(T))); |
| 93 | } |
| 94 | #endif |
| 95 | }} // namespace conversion::detail |
| 96 | |
| 97 | |
| 98 | } // namespace boost |
| 99 | |
| 100 | #endif // BOOST_LEXICAL_CAST_BAD_LEXICAL_CAST_HPP |
| 101 | |
| 102 | |