diff --git a/test/Jamfile.v2 b/test/Jamfile.v2 index f79e724..69f8b3c 100644 --- a/test/Jamfile.v2 +++ b/test/Jamfile.v2 @@ -27,5 +27,6 @@ test-suite conversion [ compile-fail implicit_cast_fail.cpp ] [ run cast_test.cpp ] [ run numeric_cast_test.cpp ] + [ run polymorphic_cast_test.cpp ] + [ compile-fail implicit_cast_fail2.cpp ] ; - diff --git a/test/implicit_cast_fail2.cpp b/test/implicit_cast_fail2.cpp new file mode 100644 index 0000000..97cc2d8 --- /dev/null +++ b/test/implicit_cast_fail2.cpp @@ -0,0 +1,19 @@ +// +// Test that implicit_cast requires a template argument +// +// Copyright 2014 Peter Dimov +// +// Distributed under the Boost Software License, Version 1.0. +// +// See accompanying file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt +// + +#include + +int main() +{ + int x = boost::implicit_cast( 1 ); + (void)x; + + return 0; +} diff --git a/test/polymorphic_cast_test.cpp b/test/polymorphic_cast_test.cpp new file mode 100644 index 0000000..b3f1397 --- /dev/null +++ b/test/polymorphic_cast_test.cpp @@ -0,0 +1,150 @@ +// +// Test boost::polymorphic_cast, boost::polymorphic_downcast +// +// Copyright 1999 Beman Dawes +// Copyright 1999 Dave Abrahams +// Copyright 2014 Peter Dimov +// +// Distributed under the Boost Software License, Version 1.0. +// +// See accompanying file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt +// + +#define BOOST_ENABLE_ASSERT_HANDLER +#include +#include +#include + +static bool expect_assertion = false; +static int assertion_failed_count = 0; + +// BOOST_ASSERT custom handler +void boost::assertion_failed( char const * expr, char const * function, char const * file, long line ) +{ + if( expect_assertion ) + { + ++assertion_failed_count; + } + else + { + BOOST_ERROR( "unexpected assertion" ); + + BOOST_LIGHTWEIGHT_TEST_OSTREAM + << file << "(" << line << "): assertion '" << expr << "' failed in function '" + << function << "'" << std::endl; + } +} + +// + +struct Base +{ + virtual ~Base() {} + virtual std::string kind() { return "Base"; } +}; + +struct Base2 +{ + virtual ~Base2() {} + virtual std::string kind2() { return "Base2"; } +}; + +struct Derived : public Base, Base2 +{ + virtual std::string kind() { return "Derived"; } +}; + +static void test_polymorphic_cast() +{ + Base * base = new Derived; + + Derived * derived; + + try + { + derived = boost::polymorphic_cast( base ); + + BOOST_TEST( derived != 0 ); + + if( derived != 0 ) + { + BOOST_TEST_EQ( derived->kind(), "Derived" ); + } + } + catch( std::bad_cast const& ) + { + BOOST_ERROR( "boost::polymorphic_cast( base ) threw std::bad_cast" ); + } + + Base2 * base2; + + try + { + base2 = boost::polymorphic_cast( base ); // crosscast + + BOOST_TEST( base2 != 0 ); + + if( base2 != 0 ) + { + BOOST_TEST_EQ( base2->kind2(), "Base2" ); + } + } + catch( std::bad_cast const& ) + { + BOOST_ERROR( "boost::polymorphic_cast( base ) threw std::bad_cast" ); + } + + delete base; +} + +static void test_polymorphic_downcast() +{ + Base * base = new Derived; + + Derived * derived = boost::polymorphic_downcast( base ); + + BOOST_TEST( derived != 0 ); + + if( derived != 0 ) + { + BOOST_TEST_EQ( derived->kind(), "Derived" ); + } + + // polymorphic_downcast can't do crosscasts + + delete base; +} + +static void test_polymorphic_cast_fail() +{ + Base * base = new Base; + + BOOST_TEST_THROWS( boost::polymorphic_cast( base ), std::bad_cast ); + + delete base; +} + +static void test_polymorphic_downcast_fail() +{ + Base * base = new Base; + + int old_count = assertion_failed_count; + expect_assertion = true; + + boost::polymorphic_downcast( base ); // should assert + + BOOST_TEST_EQ( assertion_failed_count, old_count + 1 ); + expect_assertion = false; + + delete base; +} + +int main() +{ + test_polymorphic_cast(); + test_polymorphic_downcast(); + test_polymorphic_cast_fail(); + test_polymorphic_downcast_fail(); + + return boost::report_errors(); +}