IOSS  2.0
Ioss_ScopeGuard.h
Go to the documentation of this file.
1 /*
2  * Copyright(C) 2009-2017 National Technology & Engineering Solutions
3  * of Sandia, LLC (NTESS). Under the terms of Contract DE-NA0003525 with
4  * NTESS, the U.S. Government retains certain rights in this software.
5  *
6  * Redistribution and use in source and binary forms, with or without
7  * modification, are permitted provided that the following conditions are
8  * met:
9  *
10  * * Redistributions of source code must retain the above copyright
11  * notice, this list of conditions and the following disclaimer.
12  *
13  * * Redistributions in binary form must reproduce the above
14  * copyright notice, this list of conditions and the following
15  * disclaimer in the documentation and/or other materials provided
16  * with the distribution.
17  * * Neither the name of NTESS nor the names of its
18  * contributors may be used to endorse or promote products derived
19  * from this software without specific prior written permission.
20  *
21  * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
22  * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
23  * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
24  * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
25  * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
26  * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
27  * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
28  * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
29  * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
30  * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
31  * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
32  */
33 #ifndef SCOPEGUARD_H_
34 #define SCOPEGUARD_H_
35 
36 /*
37  Scopeguard, by Andrei Alexandrescu and Petru Marginean, December 2000.
38  Modified by Joshua Lehrer, FactSet Research Systems, November 2005.
39 */
40 
41 template <class T> class RefHolder
42 {
43  T &ref_;
44 
45 public:
46  explicit RefHolder(T &ref) : ref_(ref) {}
47  operator T &() const { return ref_; }
48  RefHolder &operator=(const RefHolder &) = delete;
49 };
50 
51 template <class T> inline RefHolder<T> ByRef(T &t) { return RefHolder<T>(t); }
52 
54 {
56 
57 protected:
58  ~ScopeGuardImplBase() = default;
60  {
61  other.Dismiss();
62  }
63  template <typename J> static void SafeExecute(J &j)
64  {
65  if (!j.dismissed_) {
66  try {
67  j.Execute();
68  }
69  catch (...) {
70  }
71  }
72  }
73 
74  mutable bool dismissed_;
75 
76 public:
78  void Dismiss() const { dismissed_ = true; }
79 };
80 
81 // typedef const ScopeGuardImplBase& ScopeGuard;
82 #ifndef _MSC_VER
83 __attribute__((unused))
84 #endif
85 typedef const ScopeGuardImplBase &ScopeGuard;
86 
87 template <typename F> class ScopeGuardImpl0 : public ScopeGuardImplBase
88 {
89 public:
90  static ScopeGuardImpl0<F> MakeGuard(F fun) { return ScopeGuardImpl0<F>(fun); }
92  void Execute() { fun_(); }
93 
94 protected:
95  explicit ScopeGuardImpl0(F fun) : fun_(fun) {}
96  F fun_;
97 };
98 
99 template <typename F> inline ScopeGuardImpl0<F> MakeGuard(F fun)
100 {
101  return ScopeGuardImpl0<F>::MakeGuard(fun);
102 }
103 
104 template <typename F, typename P1> class ScopeGuardImpl1 : public ScopeGuardImplBase
105 {
106 public:
107  static ScopeGuardImpl1<F, P1> MakeGuard(F fun, P1 p1) { return ScopeGuardImpl1<F, P1>(fun, p1); }
109  void Execute() { fun_(p1_); }
110 
111 protected:
112  ScopeGuardImpl1(F fun, P1 p1) : fun_(fun), p1_(p1) {}
113  F fun_;
114  const P1 p1_;
115 };
116 
117 template <typename F, typename P1> inline ScopeGuardImpl1<F, P1> MakeGuard(F fun, P1 p1)
118 {
119  return ScopeGuardImpl1<F, P1>::MakeGuard(fun, p1);
120 }
121 
122 template <typename F, typename P1, typename P2> class ScopeGuardImpl2 : public ScopeGuardImplBase
123 {
124 public:
125  static ScopeGuardImpl2<F, P1, P2> MakeGuard(F fun, P1 p1, P2 p2)
126  {
127  return ScopeGuardImpl2<F, P1, P2>(fun, p1, p2);
128  }
130  void Execute() { fun_(p1_, p2_); }
131 
132 protected:
133  ScopeGuardImpl2(F fun, P1 p1, P2 p2) : fun_(fun), p1_(p1), p2_(p2) {}
134  F fun_;
135  const P1 p1_;
136  const P2 p2_;
137 };
138 
139 template <typename F, typename P1, typename P2>
140 inline ScopeGuardImpl2<F, P1, P2> MakeGuard(F fun, P1 p1, P2 p2)
141 {
142  return ScopeGuardImpl2<F, P1, P2>::MakeGuard(fun, p1, p2);
143 }
144 
145 template <typename F, typename P1, typename P2, typename P3>
147 {
148 public:
149  static ScopeGuardImpl3<F, P1, P2, P3> MakeGuard(F fun, P1 p1, P2 p2, P3 p3)
150  {
151  return ScopeGuardImpl3<F, P1, P2, P3>(fun, p1, p2, p3);
152  }
154  void Execute() { fun_(p1_, p2_, p3_); }
155 
156 protected:
157  ScopeGuardImpl3(F fun, P1 p1, P2 p2, P3 p3) : fun_(fun), p1_(p1), p2_(p2), p3_(p3) {}
158  F fun_;
159  const P1 p1_;
160  const P2 p2_;
161  const P3 p3_;
162 };
163 
164 template <typename F, typename P1, typename P2, typename P3>
165 inline ScopeGuardImpl3<F, P1, P2, P3> MakeGuard(F fun, P1 p1, P2 p2, P3 p3)
166 {
167  return ScopeGuardImpl3<F, P1, P2, P3>::MakeGuard(fun, p1, p2, p3);
168 }
169 
170 //************************************************************
171 
172 template <class Obj, typename MemFun> class ObjScopeGuardImpl0 : public ScopeGuardImplBase
173 {
174 public:
175  static ObjScopeGuardImpl0<Obj, MemFun> MakeObjGuard(Obj &obj, MemFun memFun)
176  {
177  return ObjScopeGuardImpl0<Obj, MemFun>(obj, memFun);
178  }
180  void Execute() { (obj_.*memFun_)(); }
181 
182 protected:
183  ObjScopeGuardImpl0(Obj &obj, MemFun memFun) : obj_(obj), memFun_(memFun) {}
184  Obj & obj_;
185  MemFun memFun_;
186 };
187 
188 template <class Obj, typename MemFun>
189 inline ObjScopeGuardImpl0<Obj, MemFun> MakeObjGuard(Obj &obj, MemFun memFun)
190 {
192 }
193 
194 template <typename Ret, class Obj1, class Obj2>
195 inline ObjScopeGuardImpl0<Obj1, Ret (Obj2::*)()> MakeGuard(Ret (Obj2::*memFun)(), Obj1 &obj)
196 {
197  return ObjScopeGuardImpl0<Obj1, Ret (Obj2::*)()>::MakeObjGuard(obj, memFun);
198 }
199 
200 template <typename Ret, class Obj1, class Obj2>
201 inline ObjScopeGuardImpl0<Obj1, Ret (Obj2::*)()> MakeGuard(Ret (Obj2::*memFun)(), Obj1 *obj)
202 {
203  return ObjScopeGuardImpl0<Obj1, Ret (Obj2::*)()>::MakeObjGuard(*obj, memFun);
204 }
205 
206 template <class Obj, typename MemFun, typename P1>
208 {
209 public:
210  static ObjScopeGuardImpl1<Obj, MemFun, P1> MakeObjGuard(Obj &obj, MemFun memFun, P1 p1)
211  {
212  return ObjScopeGuardImpl1<Obj, MemFun, P1>(obj, memFun, p1);
213  }
215  void Execute() { (obj_.*memFun_)(p1_); }
216 
217 protected:
218  ObjScopeGuardImpl1(Obj &obj, MemFun memFun, P1 p1) : obj_(obj), memFun_(memFun), p1_(p1) {}
219  Obj & obj_;
220  MemFun memFun_;
221  const P1 p1_;
222 };
223 
224 template <class Obj, typename MemFun, typename P1>
225 inline ObjScopeGuardImpl1<Obj, MemFun, P1> MakeObjGuard(Obj &obj, MemFun memFun, P1 p1)
226 {
228 }
229 
230 template <typename Ret, class Obj1, class Obj2, typename P1a, typename P1b>
231 inline ObjScopeGuardImpl1<Obj1, Ret (Obj2::*)(P1a), P1b> MakeGuard(Ret (Obj2::*memFun)(P1a),
232  Obj1 &obj, P1b p1)
233 {
234  return ObjScopeGuardImpl1<Obj1, Ret (Obj2::*)(P1a), P1b>::MakeObjGuard(obj, memFun, p1);
235 }
236 
237 template <typename Ret, class Obj1, class Obj2, typename P1a, typename P1b>
238 inline ObjScopeGuardImpl1<Obj1, Ret (Obj2::*)(P1a), P1b> MakeGuard(Ret (Obj2::*memFun)(P1a),
239  Obj1 *obj, P1b p1)
240 {
241  return ObjScopeGuardImpl1<Obj1, Ret (Obj2::*)(P1a), P1b>::MakeObjGuard(*obj, memFun, p1);
242 }
243 
244 template <class Obj, typename MemFun, typename P1, typename P2>
246 {
247 public:
248  static ObjScopeGuardImpl2<Obj, MemFun, P1, P2> MakeObjGuard(Obj &obj, MemFun memFun, P1 p1, P2 p2)
249  {
250  return ObjScopeGuardImpl2<Obj, MemFun, P1, P2>(obj, memFun, p1, p2);
251  }
253  void Execute() { (obj_.*memFun_)(p1_, p2_); }
254 
255 protected:
256  ObjScopeGuardImpl2(Obj &obj, MemFun memFun, P1 p1, P2 p2)
257  : obj_(obj), memFun_(memFun), p1_(p1), p2_(p2)
258  {
259  }
260  Obj & obj_;
261  MemFun memFun_;
262  const P1 p1_;
263  const P2 p2_;
264 };
265 
266 template <class Obj, typename MemFun, typename P1, typename P2>
267 inline ObjScopeGuardImpl2<Obj, MemFun, P1, P2> MakeObjGuard(Obj &obj, MemFun memFun, P1 p1, P2 p2)
268 {
269  return ObjScopeGuardImpl2<Obj, MemFun, P1, P2>::MakeObjGuard(obj, memFun, p1, p2);
270 }
271 
272 template <typename Ret, class Obj1, class Obj2, typename P1a, typename P1b, typename P2a,
273  typename P2b>
274 inline ObjScopeGuardImpl2<Obj1, Ret (Obj2::*)(P1a, P2a), P1b, P2b>
275 MakeGuard(Ret (Obj2::*memFun)(P1a, P2a), Obj1 &obj, P1b p1, P2b p2)
276 {
277  return ObjScopeGuardImpl2<Obj1, Ret (Obj2::*)(P1a, P2a), P1b, P2b>::MakeObjGuard(obj, memFun, p1,
278  p2);
279 }
280 
281 template <typename Ret, class Obj1, class Obj2, typename P1a, typename P1b, typename P2a,
282  typename P2b>
283 inline ObjScopeGuardImpl2<Obj1, Ret (Obj2::*)(P1a, P2a), P1b, P2b>
284 MakeGuard(Ret (Obj2::*memFun)(P1a, P2a), Obj1 *obj, P1b p1, P2b p2)
285 {
286  return ObjScopeGuardImpl2<Obj1, Ret (Obj2::*)(P1a, P2a), P1b, P2b>::MakeObjGuard(*obj, memFun, p1,
287  p2);
288 }
289 
290 #define CONCATENATE_DIRECT(s1, s2) s1##s2
291 #define CONCATENATE(s1, s2) CONCATENATE_DIRECT(s1, s2)
292 #define ANONYMOUS_VARIABLE(str) CONCATENATE(str, __LINE__)
293 
294 #define ON_BLOCK_EXIT ScopeGuard ANONYMOUS_VARIABLE(scopeGuard) = MakeGuard
295 #define ON_BLOCK_EXIT_OBJ ScopeGuard ANONYMOUS_VARIABLE(scopeGuard) = MakeObjGuard
296 
297 #endif // SCOPEGUARD_H_
ObjScopeGuardImpl0::obj_
Obj & obj_
Definition: Ioss_ScopeGuard.h:184
ScopeGuardImpl1::~ScopeGuardImpl1
~ScopeGuardImpl1()
Definition: Ioss_ScopeGuard.h:108
ObjScopeGuardImpl2::~ObjScopeGuardImpl2
~ObjScopeGuardImpl2()
Definition: Ioss_ScopeGuard.h:252
ObjScopeGuardImpl0::ObjScopeGuardImpl0
ObjScopeGuardImpl0(Obj &obj, MemFun memFun)
Definition: Ioss_ScopeGuard.h:183
ByRef
RefHolder< T > ByRef(T &t)
Definition: Ioss_ScopeGuard.h:51
ScopeGuardImpl1
Definition: Ioss_ScopeGuard.h:104
ScopeGuardImplBase
Definition: Ioss_ScopeGuard.h:53
RefHolder
Definition: Ioss_ScopeGuard.h:41
ObjScopeGuardImpl0::memFun_
MemFun memFun_
Definition: Ioss_ScopeGuard.h:185
ScopeGuardImpl3::fun_
F fun_
Definition: Ioss_ScopeGuard.h:158
RefHolder::RefHolder
RefHolder(T &ref)
Definition: Ioss_ScopeGuard.h:46
ScopeGuardImpl1::fun_
F fun_
Definition: Ioss_ScopeGuard.h:113
ScopeGuardImpl0::MakeGuard
static ScopeGuardImpl0< F > MakeGuard(F fun)
Definition: Ioss_ScopeGuard.h:90
ScopeGuardImplBase::ScopeGuardImplBase
ScopeGuardImplBase()
Definition: Ioss_ScopeGuard.h:77
ScopeGuardImplBase::dismissed_
bool dismissed_
Definition: Ioss_ScopeGuard.h:74
MakeGuard
ScopeGuardImpl0< F > MakeGuard(F fun)
Definition: Ioss_ScopeGuard.h:99
ObjScopeGuardImpl0::~ObjScopeGuardImpl0
~ObjScopeGuardImpl0()
Definition: Ioss_ScopeGuard.h:179
ObjScopeGuardImpl1::p1_
const P1 p1_
Definition: Ioss_ScopeGuard.h:221
ScopeGuardImpl0
Definition: Ioss_ScopeGuard.h:87
ScopeGuardImpl2::p2_
const P2 p2_
Definition: Ioss_ScopeGuard.h:136
ScopeGuardImpl2::Execute
void Execute()
Definition: Ioss_ScopeGuard.h:130
ObjScopeGuardImpl1::ObjScopeGuardImpl1
ObjScopeGuardImpl1(Obj &obj, MemFun memFun, P1 p1)
Definition: Ioss_ScopeGuard.h:218
ObjScopeGuardImpl2::MakeObjGuard
static ObjScopeGuardImpl2< Obj, MemFun, P1, P2 > MakeObjGuard(Obj &obj, MemFun memFun, P1 p1, P2 p2)
Definition: Ioss_ScopeGuard.h:248
ScopeGuardImpl3::p2_
const P2 p2_
Definition: Ioss_ScopeGuard.h:160
ScopeGuardImpl3
Definition: Ioss_ScopeGuard.h:146
ObjScopeGuardImpl2::obj_
Obj & obj_
Definition: Ioss_ScopeGuard.h:260
ScopeGuardImplBase::ScopeGuardImplBase
ScopeGuardImplBase(const ScopeGuardImplBase &other)
Definition: Ioss_ScopeGuard.h:59
ScopeGuardImpl3::Execute
void Execute()
Definition: Ioss_ScopeGuard.h:154
ScopeGuardImpl3::p1_
const P1 p1_
Definition: Ioss_ScopeGuard.h:159
ScopeGuardImpl1::ScopeGuardImpl1
ScopeGuardImpl1(F fun, P1 p1)
Definition: Ioss_ScopeGuard.h:112
ObjScopeGuardImpl0::MakeObjGuard
static ObjScopeGuardImpl0< Obj, MemFun > MakeObjGuard(Obj &obj, MemFun memFun)
Definition: Ioss_ScopeGuard.h:175
ObjScopeGuardImpl2
Definition: Ioss_ScopeGuard.h:245
ScopeGuardImpl2::~ScopeGuardImpl2
~ScopeGuardImpl2()
Definition: Ioss_ScopeGuard.h:129
ScopeGuardImpl2::p1_
const P1 p1_
Definition: Ioss_ScopeGuard.h:135
ObjScopeGuardImpl2::ObjScopeGuardImpl2
ObjScopeGuardImpl2(Obj &obj, MemFun memFun, P1 p1, P2 p2)
Definition: Ioss_ScopeGuard.h:256
ObjScopeGuardImpl2::Execute
void Execute()
Definition: Ioss_ScopeGuard.h:253
ObjScopeGuardImpl2::memFun_
MemFun memFun_
Definition: Ioss_ScopeGuard.h:261
MakeObjGuard
ObjScopeGuardImpl0< Obj, MemFun > MakeObjGuard(Obj &obj, MemFun memFun)
Definition: Ioss_ScopeGuard.h:189
ScopeGuardImpl1::Execute
void Execute()
Definition: Ioss_ScopeGuard.h:109
RefHolder::ref_
T & ref_
Definition: Ioss_ScopeGuard.h:43
ScopeGuardImpl2::MakeGuard
static ScopeGuardImpl2< F, P1, P2 > MakeGuard(F fun, P1 p1, P2 p2)
Definition: Ioss_ScopeGuard.h:125
ScopeGuardImpl1::MakeGuard
static ScopeGuardImpl1< F, P1 > MakeGuard(F fun, P1 p1)
Definition: Ioss_ScopeGuard.h:107
ScopeGuardImpl1::p1_
const P1 p1_
Definition: Ioss_ScopeGuard.h:114
ScopeGuardImplBase::~ScopeGuardImplBase
~ScopeGuardImplBase()=default
ScopeGuardImpl2::ScopeGuardImpl2
ScopeGuardImpl2(F fun, P1 p1, P2 p2)
Definition: Ioss_ScopeGuard.h:133
ScopeGuardImplBase::operator=
ScopeGuardImplBase & operator=(const ScopeGuardImplBase &)
ObjScopeGuardImpl1
Definition: Ioss_ScopeGuard.h:207
ObjScopeGuardImpl1::MakeObjGuard
static ObjScopeGuardImpl1< Obj, MemFun, P1 > MakeObjGuard(Obj &obj, MemFun memFun, P1 p1)
Definition: Ioss_ScopeGuard.h:210
RefHolder::operator=
RefHolder & operator=(const RefHolder &)=delete
__attribute__
__attribute__((unused)) typedef const ScopeGuardImplBase &ScopeGuard
ScopeGuardImpl0::fun_
F fun_
Definition: Ioss_ScopeGuard.h:96
ScopeGuardImpl3::MakeGuard
static ScopeGuardImpl3< F, P1, P2, P3 > MakeGuard(F fun, P1 p1, P2 p2, P3 p3)
Definition: Ioss_ScopeGuard.h:149
ScopeGuardImpl0::Execute
void Execute()
Definition: Ioss_ScopeGuard.h:92
ObjScopeGuardImpl2::p1_
const P1 p1_
Definition: Ioss_ScopeGuard.h:262
ScopeGuardImpl3::p3_
const P3 p3_
Definition: Ioss_ScopeGuard.h:161
ObjScopeGuardImpl2::p2_
const P2 p2_
Definition: Ioss_ScopeGuard.h:263
ObjScopeGuardImpl0::Execute
void Execute()
Definition: Ioss_ScopeGuard.h:180
ScopeGuardImplBase::SafeExecute
static void SafeExecute(J &j)
Definition: Ioss_ScopeGuard.h:63
ObjScopeGuardImpl1::~ObjScopeGuardImpl1
~ObjScopeGuardImpl1()
Definition: Ioss_ScopeGuard.h:214
ScopeGuardImpl0::ScopeGuardImpl0
ScopeGuardImpl0(F fun)
Definition: Ioss_ScopeGuard.h:95
ObjScopeGuardImpl1::Execute
void Execute()
Definition: Ioss_ScopeGuard.h:215
ObjScopeGuardImpl1::obj_
Obj & obj_
Definition: Ioss_ScopeGuard.h:219
ScopeGuardImpl3::~ScopeGuardImpl3
~ScopeGuardImpl3()
Definition: Ioss_ScopeGuard.h:153
ObjScopeGuardImpl1::memFun_
MemFun memFun_
Definition: Ioss_ScopeGuard.h:220
ObjScopeGuardImpl0
Definition: Ioss_ScopeGuard.h:172
ScopeGuardImpl2
Definition: Ioss_ScopeGuard.h:122
ScopeGuardImplBase::Dismiss
void Dismiss() const
Definition: Ioss_ScopeGuard.h:78
ScopeGuardImpl0::~ScopeGuardImpl0
~ScopeGuardImpl0()
Definition: Ioss_ScopeGuard.h:91
ScopeGuardImpl2::fun_
F fun_
Definition: Ioss_ScopeGuard.h:134
ScopeGuardImpl3::ScopeGuardImpl3
ScopeGuardImpl3(F fun, P1 p1, P2 p2, P3 p3)
Definition: Ioss_ScopeGuard.h:157