2 * Distributed under the Boost Software License, Version 1.0.(See accompanying
3 * file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt.)
5 * See http://www.boost.org/libs/iostreams for documentation.
7 * Tests the facilities defined in the header
8 * libs/iostreams/test/detail/operation_sequence.hpp
10 * File: libs/iostreams/test/operation_sequence_test.cpp
11 * Date: Mon Dec 10 18:58:19 MST 2007
12 * Copyright: 2007-2008 CodeRage, LLC
13 * Author: Jonathan Turkanis
14 * Contact: turkanis at coderage dot com
18 #include <boost/test/test_tools.hpp>
19 #include <boost/test/unit_test.hpp>
20 #include "detail/operation_sequence.hpp"
23 using namespace boost
;
24 using namespace boost::iostreams::test
;
25 using boost::unit_test::test_suite
;
27 // Infrastructure for checking that operations are
28 // executed in the correct order
30 void operation_sequence_test()
32 // Test creating a duplicate operation
34 operation_sequence seq
;
35 operation op
= seq
.new_operation(1);
36 BOOST_CHECK_THROW(seq
.new_operation(1), runtime_error
);
39 // Test reusing an operation id after first operation is destroyed
41 operation_sequence seq
;
43 BOOST_CHECK_NO_THROW(seq
.new_operation(1));
46 // Test creating operations with illegal error codes
48 operation_sequence seq
;
49 BOOST_CHECK_THROW(seq
.new_operation(1, -100), runtime_error
);
51 seq
.new_operation(1, BOOST_IOSTREAMS_TEST_MAX_OPERATION_ERROR
+ 1),
56 // Test two successful operations executed out of order
58 operation_sequence seq
;
59 operation op1
= seq
.new_operation(1);
60 operation op2
= seq
.new_operation(2);
61 BOOST_CHECK(!seq
.is_failure() && !seq
.is_success());
62 BOOST_CHECK_NO_THROW(op2
.execute());
63 BOOST_CHECK(!seq
.is_failure() && !seq
.is_success());
64 BOOST_CHECK_NO_THROW(op1
.execute());
65 BOOST_CHECK(seq
.is_failure());
68 // Test executing an operation twice without resetting the sequence
70 operation_sequence seq
;
71 operation op
= seq
.new_operation(1);
72 BOOST_CHECK(!seq
.is_failure() && !seq
.is_success());
73 BOOST_CHECK_NO_THROW(op
.execute());
74 BOOST_CHECK(seq
.is_success());
75 BOOST_CHECK_NO_THROW(op
.execute());
76 BOOST_CHECK(seq
.is_failure());
79 // Test creating an operation after operation execution has commenced
81 operation_sequence seq
;
82 operation op1
= seq
.new_operation(1);
83 operation op2
= seq
.new_operation(2);
85 BOOST_CHECK(!seq
.is_failure() && !seq
.is_success());
86 BOOST_CHECK_NO_THROW(op1
.execute());
87 BOOST_CHECK(!seq
.is_failure() && !seq
.is_success());
88 BOOST_CHECK_THROW(op3
= seq
.new_operation(3), runtime_error
);
89 BOOST_CHECK_NO_THROW(op2
.execute());
90 BOOST_CHECK(seq
.is_success());
93 // Test three successful operations with consecutive ids, executed in order
95 operation_sequence seq
;
96 operation op1
= seq
.new_operation(1);
97 operation op2
= seq
.new_operation(2);
98 operation op3
= seq
.new_operation(3);
101 BOOST_CHECK(!seq
.is_failure() && !seq
.is_success());
103 BOOST_CHECK(!seq
.is_failure() && !seq
.is_success());
105 BOOST_CHECK(!seq
.is_failure() && !seq
.is_success());
107 BOOST_CHECK(seq
.is_success());
111 BOOST_CHECK(!seq
.is_failure() && !seq
.is_success());
113 BOOST_CHECK(!seq
.is_failure() && !seq
.is_success());
115 BOOST_CHECK(!seq
.is_failure() && !seq
.is_success());
117 BOOST_CHECK(seq
.is_success());
120 // Test three successful operations with non-consecutive ids,
123 operation_sequence seq
;
124 operation op2
= seq
.new_operation(2);
125 operation op3
= seq
.new_operation(101);
126 operation op1
= seq
.new_operation(-43);
129 BOOST_CHECK(!seq
.is_failure() && !seq
.is_success());
131 BOOST_CHECK(!seq
.is_failure() && !seq
.is_success());
133 BOOST_CHECK(!seq
.is_failure() && !seq
.is_success());
135 BOOST_CHECK(seq
.is_success());
139 BOOST_CHECK(!seq
.is_failure() && !seq
.is_success());
141 BOOST_CHECK(!seq
.is_failure() && !seq
.is_success());
143 BOOST_CHECK(!seq
.is_failure() && !seq
.is_success());
145 BOOST_CHECK(seq
.is_success());
148 // Test checking for success after one of three operations
149 // has been destroyed
151 operation_sequence seq
;
152 operation op1
= seq
.new_operation(1);
153 operation op3
= seq
.new_operation(3);
156 operation op2
= seq
.new_operation(2);
157 BOOST_CHECK(!seq
.is_failure() && !seq
.is_success());
159 BOOST_CHECK(!seq
.is_failure() && !seq
.is_success());
161 BOOST_CHECK(!seq
.is_failure() && !seq
.is_success());
164 BOOST_CHECK(seq
.is_success());
167 // Test executing an operation sequence twice, with one of the
168 // operations replaced with a new operation with the same id
169 // in the second pass
171 operation_sequence seq
;
172 operation op1
= seq
.new_operation(1);
173 operation op3
= seq
.new_operation(3);
177 operation op2
= seq
.new_operation(2);
178 BOOST_CHECK(!seq
.is_failure() && !seq
.is_success());
180 BOOST_CHECK(!seq
.is_failure() && !seq
.is_success());
182 BOOST_CHECK(!seq
.is_failure() && !seq
.is_success());
184 BOOST_CHECK(seq
.is_success());
190 operation op2
= seq
.new_operation(2);
191 BOOST_CHECK(!seq
.is_failure() && !seq
.is_success());
193 BOOST_CHECK(!seq
.is_failure() && !seq
.is_success());
195 BOOST_CHECK(!seq
.is_failure() && !seq
.is_success());
197 BOOST_CHECK(seq
.is_success());
201 // Test three operations executed in order, the first of which throws
203 operation_sequence seq
;
204 operation op1
= seq
.new_operation(1, 1);
205 operation op2
= seq
.new_operation(2);
206 operation op3
= seq
.new_operation(3);
207 BOOST_CHECK(!seq
.is_failure() && !seq
.is_success());
208 BOOST_CHECK_THROW(op1
.execute(), operation_error
<1>);
209 BOOST_CHECK(!seq
.is_failure() && !seq
.is_success());
210 BOOST_CHECK_NO_THROW(op2
.execute());
211 BOOST_CHECK(!seq
.is_failure() && !seq
.is_success());
212 BOOST_CHECK_NO_THROW(op3
.execute());
213 BOOST_CHECK(seq
.is_success());
216 // Test three operations executed in order, the second of which throws
218 operation_sequence seq
;
219 operation op1
= seq
.new_operation(1);
220 operation op2
= seq
.new_operation(2, 2);
221 operation op3
= seq
.new_operation(3);
222 BOOST_CHECK(!seq
.is_failure() && !seq
.is_success());
223 BOOST_CHECK_NO_THROW(op1
.execute());
224 BOOST_CHECK(!seq
.is_failure() && !seq
.is_success());
225 BOOST_CHECK_THROW(op2
.execute(), operation_error
<2>);
226 BOOST_CHECK(!seq
.is_failure() && !seq
.is_success());
227 BOOST_CHECK_NO_THROW(op3
.execute());
228 BOOST_CHECK(seq
.is_success());
231 // Test three operations executed in order, the third of which throws
233 operation_sequence seq
;
234 operation op1
= seq
.new_operation(1);
235 operation op2
= seq
.new_operation(2);
236 operation op3
= seq
.new_operation(3, 3);
237 BOOST_CHECK(!seq
.is_failure() && !seq
.is_success());
238 BOOST_CHECK_NO_THROW(op1
.execute());
239 BOOST_CHECK(!seq
.is_failure() && !seq
.is_success());
240 BOOST_CHECK_NO_THROW(op2
.execute());
241 BOOST_CHECK(!seq
.is_failure() && !seq
.is_success());
242 BOOST_CHECK_THROW(op3
.execute(), operation_error
<3>);
243 BOOST_CHECK(seq
.is_success());
246 // Test three operations executed in order, the first and
247 // third of which throw
249 operation_sequence seq
;
250 operation op1
= seq
.new_operation(1, 1);
251 operation op2
= seq
.new_operation(2);
252 operation op3
= seq
.new_operation(3, 3);
253 BOOST_CHECK(!seq
.is_failure() && !seq
.is_success());
254 BOOST_CHECK_THROW(op1
.execute(), operation_error
<1>);
255 BOOST_CHECK(!seq
.is_failure() && !seq
.is_success());
256 BOOST_CHECK_NO_THROW(op2
.execute());
257 BOOST_CHECK(!seq
.is_failure() && !seq
.is_success());
258 BOOST_CHECK_THROW(op3
.execute(), operation_error
<3>);
259 BOOST_CHECK(seq
.is_success());
263 test_suite
* init_unit_test_suite(int, char* [])
265 test_suite
* test
= BOOST_TEST_SUITE("execute test");
266 test
->add(BOOST_TEST_CASE(&operation_sequence_test
));