
Thorsten Ottosen skrev:
Joaquin M Lopez Munoz skrev:
Thorsten Ottosen <nesotto <at> cs.aau.dk> writes:
Would you like to do the addition yourself and commit the changes to the trunk? I'm quite busy these days to do it myself.
Yes, no problem.
I'll post the code here before comitting.
Attached is a patch. I have used the header in my own code like so: #define BOOST_AUTO_BUFFER_CONSTRUCTOR_SCOPE_GUARD() \ boost::multi_index::detail::make_obj_guard_if<boost::has_nothrow_copy<T>::value>( *this, \ &auto_buffer::deallocate, \ buffer_, members_.capacity_ ) #define BOOST_AUTO_BUFFER_LOCAL_SCOPE_GUARD( BUFFER, CAPACITY ) \ boost::multi_index::detail::make_obj_guard_if<boost::has_nothrow_copy<T>::value>( *this, \ &auto_buffer::deallocate, \ (BUFFER), (CAPACITY) ) Let me know if it is good enough to be committed. regards -Thorsten Index: scope_guard.hpp =================================================================== --- scope_guard.hpp (revision 61481) +++ scope_guard.hpp (working copy) @@ -88,12 +88,48 @@ F fun_; }; +struct null_guard : public scope_guard_impl_base +{ + template< class T1 > + null_guard( const T1& ) + { } + + template< class T1, class T2 > + null_guard( const T1&, const T2& ) + { } + + template< class T1, class T2, class T3 > + null_guard( const T1&, const T2&, const T3& ) + { } + + template< class T1, class T2, class T3, class T4 > + null_guard( const T1&, const T2&, const T3&, const T4& ) + { } + + template< class T1, class T2, class T3, class T4, class T5 > + null_guard( const T1&, const T2&, const T3&, const T4&, const T5& ) + { } +}; + +template< bool is_null, class T > +struct null_guard_return +{ + typedef typename boost::mpl::if_c<is_null,null_guard,T>::type type; +}; + template<typename F> inline scope_guard_impl0<F> make_guard(F fun) { return scope_guard_impl0<F>(fun); } +template<bool is_null, typename F> +inline typename null_guard_return<is_null,scope_guard_impl0<F> >::type +make_guard_if(F fun) +{ + return typename null_guard_return<is_null,scope_guard_impl0<F> >::type(fun); +} + template<typename F,typename P1> class scope_guard_impl1:public scope_guard_impl_base { @@ -113,6 +149,13 @@ return scope_guard_impl1<F,P1>(fun,p1); } +template<bool is_null, typename F,typename P1> +inline typename null_guard_return<is_null,scope_guard_impl1<F,P1> >::type +make_guard_if(F fun,P1 p1) +{ + return typename null_guard_return<is_null,scope_guard_impl1<F,P1> >::type(fun,p1); +} + template<typename F,typename P1,typename P2> class scope_guard_impl2:public scope_guard_impl_base { @@ -133,6 +176,13 @@ return scope_guard_impl2<F,P1,P2>(fun,p1,p2); } +template<bool is_null, typename F,typename P1,typename P2> +inline typename null_guard_return<is_null,scope_guard_impl2<F,P1,P2> >::type +make_guard_if(F fun,P1 p1,P2 p2) +{ + return typename null_guard_return<is_null,scope_guard_impl2<F,P1,P2> >::type(fun,p1,p2); +} + template<typename F,typename P1,typename P2,typename P3> class scope_guard_impl3:public scope_guard_impl_base { @@ -154,6 +204,13 @@ return scope_guard_impl3<F,P1,P2,P3>(fun,p1,p2,p3); } +template<bool is_null,typename F,typename P1,typename P2,typename P3> +inline typename null_guard_return<is_null,scope_guard_impl3<F,P1,P2,P3> >::type +make_guard_if(F fun,P1 p1,P2 p2,P3 p3) +{ + return typename null_guard_return<is_null,scope_guard_impl3<F,P1,P2,P3> >::type(fun,p1,p2,p3); +} + template<typename F,typename P1,typename P2,typename P3,typename P4> class scope_guard_impl4:public scope_guard_impl_base { @@ -178,6 +235,14 @@ return scope_guard_impl4<F,P1,P2,P3,P4>(fun,p1,p2,p3,p4); } +template<bool is_null, typename F,typename P1,typename P2,typename P3,typename P4> +inline typename null_guard_return<is_null,scope_guard_impl4<F,P1,P2,P3,P4> >::type +make_guard_if( + F fun,P1 p1,P2 p2,P3 p3,P4 p4) +{ + return typename null_guard_return<is_null,scope_guard_impl4<F,P1,P2,P3,P4> >::type(fun,p1,p2,p3,p4); +} + template<class Obj,typename MemFun> class obj_scope_guard_impl0:public scope_guard_impl_base { @@ -197,6 +262,13 @@ return obj_scope_guard_impl0<Obj,MemFun>(obj,mem_fun); } +template<bool is_null, class Obj,typename MemFun> +inline typename null_guard_return<is_null,obj_scope_guard_impl0<Obj,MemFun> >::type +make_obj_guard_if(Obj& obj,MemFun mem_fun) +{ + return typename null_guard_return<is_null,obj_scope_guard_impl0<Obj,MemFun> >::type(obj,mem_fun); +} + template<class Obj,typename MemFun,typename P1> class obj_scope_guard_impl1:public scope_guard_impl_base { @@ -219,6 +291,13 @@ return obj_scope_guard_impl1<Obj,MemFun,P1>(obj,mem_fun,p1); } +template<bool is_null, class Obj,typename MemFun,typename P1> +inline typename null_guard_return<is_null,obj_scope_guard_impl1<Obj,MemFun,P1> >::type +make_obj_guard_if( Obj& obj,MemFun mem_fun,P1 p1) +{ + return typename null_guard_return<is_null,obj_scope_guard_impl1<Obj,MemFun,P1> >::type(obj,mem_fun,p1); +} + template<class Obj,typename MemFun,typename P1,typename P2> class obj_scope_guard_impl2:public scope_guard_impl_base { @@ -243,6 +322,13 @@ return obj_scope_guard_impl2<Obj,MemFun,P1,P2>(obj,mem_fun,p1,p2); } +template<bool is_null, class Obj,typename MemFun,typename P1,typename P2> +inline typename null_guard_return<is_null,obj_scope_guard_impl2<Obj,MemFun,P1,P2> >::type +make_obj_guard_if(Obj& obj,MemFun mem_fun,P1 p1,P2 p2) +{ + return typename null_guard_return<is_null,obj_scope_guard_impl2<Obj,MemFun,P1,P2> >::type(obj,mem_fun,p1,p2); +} + template<class Obj,typename MemFun,typename P1,typename P2,typename P3> class obj_scope_guard_impl3:public scope_guard_impl_base { @@ -268,6 +354,13 @@ return obj_scope_guard_impl3<Obj,MemFun,P1,P2,P3>(obj,mem_fun,p1,p2,p3); } +template<bool is_null, class Obj,typename MemFun,typename P1,typename P2,typename P3> +inline typename null_guard_return<is_null,obj_scope_guard_impl3<Obj,MemFun,P1,P2,P3> >::type +make_obj_guard_if(Obj& obj,MemFun mem_fun,P1 p1,P2 p2,P3 p3) +{ + return typename null_guard_return<is_null,obj_scope_guard_impl3<Obj,MemFun,P1,P2,P3> >::type(obj,mem_fun,p1,p2,p3); +} + } /* namespace multi_index::detail */ } /* namespace multi_index */