added iOS source code
[wl-app.git] / iOS / Pods / Realm / include / core / realm / util / scope_exit.hpp
1 /*************************************************************************
2  *
3  * Copyright 2016 Realm Inc.
4  *
5  * Licensed under the Apache License, Version 2.0 (the "License");
6  * you may not use this file except in compliance with the License.
7  * You may obtain a copy of the License at
8  *
9  * http://www.apache.org/licenses/LICENSE-2.0
10  *
11  * Unless required by applicable law or agreed to in writing, software
12  * distributed under the License is distributed on an "AS IS" BASIS,
13  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14  * See the License for the specific language governing permissions and
15  * limitations under the License.
16  *
17  **************************************************************************/
18
19 #ifndef REALM_UTIL_SCOPE_EXIT_HPP
20 #define REALM_UTIL_SCOPE_EXIT_HPP
21
22 #include <type_traits>
23 #include <utility>
24
25 #include <realm/util/optional.hpp>
26
27 namespace realm {
28 namespace util {
29
30 template <class H>
31 class ScopeExit {
32 public:
33     explicit ScopeExit(const H& handler) noexcept(std::is_nothrow_copy_constructible<H>::value)
34         : m_handler(handler)
35     {
36     }
37
38     explicit ScopeExit(H&& handler) noexcept(std::is_nothrow_move_constructible<H>::value)
39         : m_handler(std::move(handler))
40     {
41     }
42
43     ScopeExit(ScopeExit&& se) noexcept(std::is_nothrow_move_constructible<H>::value)
44         : m_handler(std::move(se.m_handler))
45     {
46         se.m_handler = none;
47     }
48
49     ~ScopeExit() noexcept
50     {
51         if (m_handler)
52             (*m_handler)();
53     }
54
55     static_assert(noexcept(std::declval<H>()()), "Handler must be nothrow executable");
56     static_assert(std::is_nothrow_destructible<H>::value, "Handler must be nothrow destructible");
57
58 private:
59     util::Optional<H> m_handler;
60 };
61
62 template <class H>
63 ScopeExit<typename std::remove_reference<H>::type> make_scope_exit(H&& handler) noexcept(
64     noexcept(ScopeExit<typename std::remove_reference<H>::type>(std::forward<H>(handler))))
65 {
66     return ScopeExit<typename std::remove_reference<H>::type>(std::forward<H>(handler));
67 }
68
69 } // namespace util
70 } // namespace realm
71
72 #endif // REALM_UTIL_SCOPE_EXIT_HPP