Imported Upstream version 1.57.0
[platform/upstream/boost.git] / libs / scope_exit / test / native.cpp
1
2 // Copyright (C) 2006-2009, 2012 Alexander Nasonov
3 // Copyright (C) 2012 Lorenzo Caminiti
4 // Distributed under the Boost Software License, Version 1.0
5 // (see accompanying file LICENSE_1_0.txt or a copy at
6 // http://www.boost.org/LICENSE_1_0.txt)
7 // Home at http://www.boost.org/libs/scope_exit
8
9 #include <boost/scope_exit.hpp>
10 #include <boost/config.hpp>
11 #include <boost/typeof/typeof.hpp>
12 #include <boost/typeof/std/string.hpp>
13 #include <boost/detail/lightweight_test.hpp>
14 #include <iostream>
15 #include <ostream>
16 #include <string>
17
18 std::string g_str;
19
20 template<int Dummy = 0>
21 struct Holder {
22     static long g_long;
23 };
24
25 template<int Dummy> long Holder<Dummy>::g_long;
26
27 void test_non_local(void) {
28     // ... and one local variable as well:
29     int i = 0;
30
31     BOOST_SCOPE_EXIT(void) {
32         BOOST_TEST(Holder<>::g_long == 3);
33     } BOOST_SCOPE_EXIT_END
34
35     BOOST_SCOPE_EXIT( (i) ) {
36         BOOST_TEST(i == 0);
37         BOOST_TEST(Holder<>::g_long == 3);
38         BOOST_TEST(g_str == "try: g_str");
39     } BOOST_SCOPE_EXIT_END
40
41     BOOST_SCOPE_EXIT( (&i) ) {
42         BOOST_TEST(i == 3);
43         BOOST_TEST(Holder<>::g_long == 3);
44         BOOST_TEST(g_str == "try: g_str");
45     } BOOST_SCOPE_EXIT_END
46
47     {
48         g_str = "";
49         Holder<>::g_long = 1;
50
51         BOOST_SCOPE_EXIT( (&i) ) {
52             i = 1;
53             g_str = "g_str";
54         } BOOST_SCOPE_EXIT_END
55
56         BOOST_SCOPE_EXIT( (&i) ) {
57             try {
58                 i = 2;
59                 Holder<>::g_long = 2;
60                 throw 0;
61             } catch(...) {}
62         } BOOST_SCOPE_EXIT_END
63
64         BOOST_TEST(i == 0);
65         BOOST_TEST(g_str == "");
66         BOOST_TEST(Holder<>::g_long == 1);
67     }
68
69     BOOST_TEST(Holder<>::g_long == 2);
70     BOOST_TEST(g_str == "g_str");
71     BOOST_TEST(i == 1); // Check that first declared is executed last.
72
73     BOOST_SCOPE_EXIT( (&i) ) {
74         BOOST_TEST(i == 3);
75         BOOST_TEST(Holder<>::g_long == 3);
76         BOOST_TEST(g_str == "try: g_str");
77     } BOOST_SCOPE_EXIT_END
78
79     BOOST_SCOPE_EXIT( (i) ) {
80         BOOST_TEST(i == 1);
81         BOOST_TEST(Holder<>::g_long == 3);
82         BOOST_TEST(g_str == "try: g_str");
83     } BOOST_SCOPE_EXIT_END
84
85     try {
86         BOOST_SCOPE_EXIT( (&i) ) {
87             i = 3;
88             g_str = "try: g_str";
89         } BOOST_SCOPE_EXIT_END
90         
91         BOOST_SCOPE_EXIT( (&i) ) {
92             i = 4;
93             Holder<>::g_long = 3;
94         } BOOST_SCOPE_EXIT_END
95
96         BOOST_TEST(i == 1);
97         BOOST_TEST(g_str == "g_str");
98         BOOST_TEST(Holder<>::g_long == 2);
99
100         throw 0;
101     } catch(int) {
102         BOOST_TEST(Holder<>::g_long == 3);
103         BOOST_TEST(g_str == "try: g_str");
104         BOOST_TEST(i == 3); // Check that first declared is executed last.
105     }
106 }
107
108 bool foo(void) { return true; }
109
110 bool foo2(void) { return false; }
111
112 void test_types(void) {
113     bool (*pf)(void) = 0;
114     bool (&rf)(void) = foo;
115     bool results[2] = {};
116
117     {
118         BOOST_SCOPE_EXIT( (&results) (&pf) (&rf) ) {
119             results[0] = pf();
120             results[1] = rf();
121         }
122         BOOST_SCOPE_EXIT_END
123
124         pf = &foo;
125
126         BOOST_TEST(results[0] == false);
127         BOOST_TEST(results[1] == false);
128     }
129
130     BOOST_TEST(results[0] == true);
131     BOOST_TEST(results[1] == true);
132
133     {
134         BOOST_SCOPE_EXIT( (&results) (pf) ) {
135             results[0] = !pf();
136             results[1] = !pf();
137             pf = &foo2; // modify a copy
138         }
139         BOOST_SCOPE_EXIT_END
140
141         pf = 0;
142
143         BOOST_TEST(results[0] == true);
144         BOOST_TEST(results[1] == true);
145     }
146
147     BOOST_TEST(pf == 0);
148     BOOST_TEST(results[0] == false);
149     BOOST_TEST(results[1] == false);
150 }
151
152 void test_capture_all(void) {
153 #ifndef BOOST_NO_CXX11_LAMBDAS
154     int i = 0, j = 1;
155
156     {
157         BOOST_SCOPE_EXIT_ALL(=) {
158             i = j = 1; // modify copies
159         };
160     }
161     BOOST_TEST(i == 0);
162     BOOST_TEST(j == 1);
163
164     {
165         BOOST_SCOPE_EXIT_ALL(&) {
166             i = 1;
167             j = 2;
168         };
169         BOOST_TEST(i == 0);
170         BOOST_TEST(j == 1);
171     }
172     BOOST_TEST(i == 1);
173     BOOST_TEST(j == 2);
174
175     {
176         BOOST_SCOPE_EXIT_ALL(=, &j) {
177             i = 2; // modify a copy
178             j = 3;
179         };
180         BOOST_TEST(i == 1);
181         BOOST_TEST(j == 2);
182     }
183     BOOST_TEST(i == 1);
184     BOOST_TEST(j == 3);
185 #endif // lambdas
186 }
187
188 int main(void) {
189     test_non_local();
190     test_types();
191     test_capture_all();
192     return boost::report_errors();
193 }
194