summaryrefslogtreecommitdiffstats
path: root/src/boost/libs/lambda/test/exception_test.cpp
diff options
context:
space:
mode:
Diffstat (limited to 'src/boost/libs/lambda/test/exception_test.cpp')
-rw-r--r--src/boost/libs/lambda/test/exception_test.cpp618
1 files changed, 618 insertions, 0 deletions
diff --git a/src/boost/libs/lambda/test/exception_test.cpp b/src/boost/libs/lambda/test/exception_test.cpp
new file mode 100644
index 000000000..661541f30
--- /dev/null
+++ b/src/boost/libs/lambda/test/exception_test.cpp
@@ -0,0 +1,618 @@
+// -- exception_test.cpp -- The Boost Lambda Library ------------------
+//
+// Copyright (C) 2000-2003 Jaakko Jarvi (jaakko.jarvi@cs.utu.fi)
+// Copyright (C) 2000-2003 Gary Powell (powellg@amazon.com)
+//
+// 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)
+//
+// For more information, see www.boost.org
+
+// -----------------------------------------------------------------------
+
+#include <boost/core/lightweight_test.hpp>
+#define BOOST_CHECK BOOST_TEST
+
+#include "boost/lambda/lambda.hpp"
+
+#include "boost/lambda/exceptions.hpp"
+
+#include "boost/lambda/bind.hpp"
+
+#include<iostream>
+#include<algorithm>
+#include <cstdlib>
+
+#include <iostream>
+
+using namespace boost::lambda;
+using namespace std;
+
+// to prevent unused variables warnings
+template <class T> void dummy(const T&) {}
+
+void erroneous_exception_related_lambda_expressions() {
+
+ int i = 0;
+ dummy(i);
+
+ // Uncommenting any of the below code lines should result in a compile
+ // time error
+
+ // this should fail (a rethrow binder outside of catch
+ // rethrow()();
+
+ // this should fail too for the same reason
+ // try_catch(rethrow(), catch_all(cout << constant("Howdy")))();
+
+ // this fails too (_e outside of catch_exception)
+ // (_1 + _2 + _e)(i, i, i);
+
+ // and this (_e outside of catch_exception)
+ // try_catch( throw_exception(1), catch_all(cout << _e));
+
+ // and this (_3 in catch_exception
+ // try_catch( throw_exception(1), catch_exception<int>(cout << _3));
+}
+
+
+class A1 {};
+class A2 {};
+class A3 {};
+class A4 {};
+class A5 {};
+class A6 {};
+class A7 {};
+class A8 {};
+class A9 {};
+
+void throw_AX(int j) {
+ int i = j;
+ switch(i) {
+ case 1: throw A1();
+ case 2: throw A2();
+ case 3: throw A3();
+ case 4: throw A4();
+ case 5: throw A5();
+ case 6: throw A6();
+ case 7: throw A7();
+ case 8: throw A8();
+ case 9: throw A9();
+ }
+}
+
+void test_different_number_of_catch_blocks() {
+
+ int ecount;
+
+// no catch(...) cases
+
+
+ ecount = 0;
+ for(int i=1; i<=1; i++)
+ {
+ try_catch(
+ bind(throw_AX, _1),
+ catch_exception<A1>(
+ var(ecount)++
+ )
+ )(i);
+ }
+ BOOST_CHECK(ecount == 1);
+
+ ecount = 0;
+ for(int i=1; i<=2; i++)
+ {
+ try_catch(
+ bind(throw_AX, _1),
+ catch_exception<A1>(
+ var(ecount)++
+ ),
+ catch_exception<A2>(
+ var(ecount)++
+ )
+ )(i);
+ }
+ BOOST_CHECK(ecount == 2);
+
+ ecount = 0;
+ for(int i=1; i<=3; i++)
+ {
+ try_catch(
+ bind(throw_AX, _1),
+ catch_exception<A1>(
+ var(ecount)++
+ ),
+ catch_exception<A2>(
+ var(ecount)++
+ ),
+ catch_exception<A3>(
+ var(ecount)++
+ )
+ )(i);
+ }
+ BOOST_CHECK(ecount == 3);
+
+ ecount = 0;
+ for(int i=1; i<=4; i++)
+ {
+ try_catch(
+ bind(throw_AX, _1),
+ catch_exception<A1>(
+ var(ecount)++
+ ),
+ catch_exception<A2>(
+ var(ecount)++
+ ),
+ catch_exception<A3>(
+ var(ecount)++
+ ),
+ catch_exception<A4>(
+ var(ecount)++
+ )
+ )(i);
+ }
+ BOOST_CHECK(ecount == 4);
+
+ ecount = 0;
+ for(int i=1; i<=5; i++)
+ {
+ try_catch(
+ bind(throw_AX, _1),
+ catch_exception<A1>(
+ var(ecount)++
+ ),
+ catch_exception<A2>(
+ var(ecount)++
+ ),
+ catch_exception<A3>(
+ var(ecount)++
+ ),
+ catch_exception<A4>(
+ var(ecount)++
+ ),
+ catch_exception<A5>(
+ var(ecount)++
+ )
+ )(i);
+ }
+ BOOST_CHECK(ecount == 5);
+
+ ecount = 0;
+ for(int i=1; i<=6; i++)
+ {
+ try_catch(
+ bind(throw_AX, _1),
+ catch_exception<A1>(
+ var(ecount)++
+ ),
+ catch_exception<A2>(
+ var(ecount)++
+ ),
+ catch_exception<A3>(
+ var(ecount)++
+ ),
+ catch_exception<A4>(
+ var(ecount)++
+ ),
+ catch_exception<A5>(
+ var(ecount)++
+ ),
+ catch_exception<A6>(
+ var(ecount)++
+ )
+ )(i);
+ }
+ BOOST_CHECK(ecount == 6);
+
+ ecount = 0;
+ for(int i=1; i<=7; i++)
+ {
+ try_catch(
+ bind(throw_AX, _1),
+ catch_exception<A1>(
+ var(ecount)++
+ ),
+ catch_exception<A2>(
+ var(ecount)++
+ ),
+ catch_exception<A3>(
+ var(ecount)++
+ ),
+ catch_exception<A4>(
+ var(ecount)++
+ ),
+ catch_exception<A5>(
+ var(ecount)++
+ ),
+ catch_exception<A6>(
+ var(ecount)++
+ ),
+ catch_exception<A7>(
+ var(ecount)++
+ )
+ )(i);
+ }
+ BOOST_CHECK(ecount == 7);
+
+ ecount = 0;
+ for(int i=1; i<=8; i++)
+ {
+ try_catch(
+ bind(throw_AX, _1),
+ catch_exception<A1>(
+ var(ecount)++
+ ),
+ catch_exception<A2>(
+ var(ecount)++
+ ),
+ catch_exception<A3>(
+ var(ecount)++
+ ),
+ catch_exception<A4>(
+ var(ecount)++
+ ),
+ catch_exception<A5>(
+ var(ecount)++
+ ),
+ catch_exception<A6>(
+ var(ecount)++
+ ),
+ catch_exception<A7>(
+ var(ecount)++
+ ),
+ catch_exception<A8>(
+ var(ecount)++
+ )
+ )(i);
+ }
+ BOOST_CHECK(ecount == 8);
+
+ ecount = 0;
+ for(int i=1; i<=9; i++)
+ {
+ try_catch(
+ bind(throw_AX, _1),
+ catch_exception<A1>(
+ var(ecount)++
+ ),
+ catch_exception<A2>(
+ var(ecount)++
+ ),
+ catch_exception<A3>(
+ var(ecount)++
+ ),
+ catch_exception<A4>(
+ var(ecount)++
+ ),
+ catch_exception<A5>(
+ var(ecount)++
+ ),
+ catch_exception<A6>(
+ var(ecount)++
+ ),
+ catch_exception<A7>(
+ var(ecount)++
+ ),
+ catch_exception<A8>(
+ var(ecount)++
+ ),
+ catch_exception<A9>(
+ var(ecount)++
+ )
+ )(i);
+ }
+ BOOST_CHECK(ecount == 9);
+
+
+ // with catch(...) blocks
+
+ ecount = 0;
+ for(int i=1; i<=1; i++)
+ {
+ try_catch(
+ bind(throw_AX, _1),
+ catch_all(
+ var(ecount)++
+ )
+ )(i);
+ }
+ BOOST_CHECK(ecount == 1);
+
+ ecount = 0;
+ for(int i=1; i<=2; i++)
+ {
+ try_catch(
+ bind(throw_AX, _1),
+ catch_exception<A1>(
+ var(ecount)++
+ ),
+ catch_all(
+ var(ecount)++
+ )
+ )(i);
+ }
+ BOOST_CHECK(ecount == 2);
+
+ ecount = 0;
+ for(int i=1; i<=3; i++)
+ {
+ try_catch(
+ bind(throw_AX, _1),
+ catch_exception<A1>(
+ var(ecount)++
+ ),
+ catch_exception<A2>(
+ var(ecount)++
+ ),
+ catch_all(
+ var(ecount)++
+ )
+ )(i);
+ }
+ BOOST_CHECK(ecount == 3);
+
+ ecount = 0;
+ for(int i=1; i<=4; i++)
+ {
+ try_catch(
+ bind(throw_AX, _1),
+ catch_exception<A1>(
+ var(ecount)++
+ ),
+ catch_exception<A2>(
+ var(ecount)++
+ ),
+ catch_exception<A3>(
+ var(ecount)++
+ ),
+ catch_all(
+ var(ecount)++
+ )
+ )(i);
+ }
+ BOOST_CHECK(ecount == 4);
+
+ ecount = 0;
+ for(int i=1; i<=5; i++)
+ {
+ try_catch(
+ bind(throw_AX, _1),
+ catch_exception<A1>(
+ var(ecount)++
+ ),
+ catch_exception<A2>(
+ var(ecount)++
+ ),
+ catch_exception<A3>(
+ var(ecount)++
+ ),
+ catch_exception<A4>(
+ var(ecount)++
+ ),
+ catch_all(
+ var(ecount)++
+ )
+ )(i);
+ }
+ BOOST_CHECK(ecount == 5);
+
+ ecount = 0;
+ for(int i=1; i<=6; i++)
+ {
+ try_catch(
+ bind(throw_AX, _1),
+ catch_exception<A1>(
+ var(ecount)++
+ ),
+ catch_exception<A2>(
+ var(ecount)++
+ ),
+ catch_exception<A3>(
+ var(ecount)++
+ ),
+ catch_exception<A4>(
+ var(ecount)++
+ ),
+ catch_exception<A5>(
+ var(ecount)++
+ ),
+ catch_all(
+ var(ecount)++
+ )
+ )(i);
+ }
+ BOOST_CHECK(ecount == 6);
+
+ ecount = 0;
+ for(int i=1; i<=7; i++)
+ {
+ try_catch(
+ bind(throw_AX, _1),
+ catch_exception<A1>(
+ var(ecount)++
+ ),
+ catch_exception<A2>(
+ var(ecount)++
+ ),
+ catch_exception<A3>(
+ var(ecount)++
+ ),
+ catch_exception<A4>(
+ var(ecount)++
+ ),
+ catch_exception<A5>(
+ var(ecount)++
+ ),
+ catch_exception<A6>(
+ var(ecount)++
+ ),
+ catch_all(
+ var(ecount)++
+ )
+ )(i);
+ }
+ BOOST_CHECK(ecount == 7);
+
+ ecount = 0;
+ for(int i=1; i<=8; i++)
+ {
+ try_catch(
+ bind(throw_AX, _1),
+ catch_exception<A1>(
+ var(ecount)++
+ ),
+ catch_exception<A2>(
+ var(ecount)++
+ ),
+ catch_exception<A3>(
+ var(ecount)++
+ ),
+ catch_exception<A4>(
+ var(ecount)++
+ ),
+ catch_exception<A5>(
+ var(ecount)++
+ ),
+ catch_exception<A6>(
+ var(ecount)++
+ ),
+ catch_exception<A7>(
+ var(ecount)++
+ ),
+ catch_all(
+ var(ecount)++
+ )
+ )(i);
+ }
+ BOOST_CHECK(ecount == 8);
+
+ ecount = 0;
+ for(int i=1; i<=9; i++)
+ {
+ try_catch(
+ bind(throw_AX, _1),
+ catch_exception<A1>(
+ var(ecount)++
+ ),
+ catch_exception<A2>(
+ var(ecount)++
+ ),
+ catch_exception<A3>(
+ var(ecount)++
+ ),
+ catch_exception<A4>(
+ var(ecount)++
+ ),
+ catch_exception<A5>(
+ var(ecount)++
+ ),
+ catch_exception<A6>(
+ var(ecount)++
+ ),
+ catch_exception<A7>(
+ var(ecount)++
+ ),
+ catch_exception<A8>(
+ var(ecount)++
+ ),
+ catch_all(
+ var(ecount)++
+ )
+ )(i);
+ }
+ BOOST_CHECK(ecount == 9);
+}
+
+void test_empty_catch_blocks() {
+ try_catch(
+ bind(throw_AX, _1),
+ catch_exception<A1>()
+ )(make_const(1));
+
+ try_catch(
+ bind(throw_AX, _1),
+ catch_all()
+ )(make_const(1));
+
+}
+
+
+void return_type_matching() {
+
+// Rules for return types of the lambda functors in try and catch parts:
+// 1. The try part dictates the return type of the whole
+// try_catch lambda functor
+// 2. If return type of try part is void, catch parts can return anything,
+// but the return types are ignored
+// 3. If the return type of the try part is A, then each catch return type
+// must be implicitly convertible to A, or then it must throw for sure
+
+
+ int i = 1;
+
+ BOOST_CHECK(
+
+ try_catch(
+ _1 + 1,
+ catch_exception<int>((&_1, rethrow())), // no match, but ok since throws
+ catch_exception<char>(_e) // ok, char convertible to int
+ )(i)
+
+ == 2
+ );
+
+ // note that while e.g. char is convertible to int, it is not convertible
+ // to int&, (some lambda functors return references)
+
+ // try_catch(
+ // _1 += 1,
+ // catch_exception<char>(_e) // NOT ok, char not convertible to int&
+ // )(i);
+
+ // if you don't care about the return type, you can use make_void
+ try_catch(
+ make_void(_1 += 1),
+ catch_exception<char>(_e) // since try is void, catch can return anything
+ )(i);
+ BOOST_CHECK(i == 2);
+
+ try_catch(
+ (_1 += 1, throw_exception('a')),
+ catch_exception<char>(_e) // since try throws, it is void,
+ // so catch can return anything
+ )(i);
+ BOOST_CHECK(i == 3);
+
+ char a = 'a';
+ try_catch(
+ try_catch(
+ throw_exception(1),
+ catch_exception<int>(throw_exception('b'))
+ ),
+ catch_exception<char>( _1 = _e )
+ )(a);
+ BOOST_CHECK(a == 'b');
+}
+
+int main() {
+
+ try
+ {
+ test_different_number_of_catch_blocks();
+ return_type_matching();
+ test_empty_catch_blocks();
+ }
+ catch (int)
+ {
+ BOOST_CHECK(false);
+ }
+ catch(...)
+ {
+ BOOST_CHECK(false);
+ }
+
+
+ return boost::report_errors();
+}