Chris@102
|
1 /////////////////////////////////////////////////////////////////////////////
|
Chris@102
|
2 //
|
Chris@102
|
3 // (C) Copyright Ion Gaztanaga 2014-2014
|
Chris@102
|
4 //
|
Chris@102
|
5 // Distributed under the Boost Software License, Version 1.0.
|
Chris@102
|
6 // (See accompanying file LICENSE_1_0.txt or copy at
|
Chris@102
|
7 // http://www.boost.org/LICENSE_1_0.txt)
|
Chris@102
|
8 //
|
Chris@102
|
9 // See http://www.boost.org/libs/intrusive for documentation.
|
Chris@102
|
10 //
|
Chris@102
|
11 /////////////////////////////////////////////////////////////////////////////
|
Chris@102
|
12
|
Chris@102
|
13 #ifndef BOOST_INTRUSIVE_DETAIL_ARRAY_INITIALIZER_HPP
|
Chris@102
|
14 #define BOOST_INTRUSIVE_DETAIL_ARRAY_INITIALIZER_HPP
|
Chris@102
|
15
|
Chris@102
|
16 #ifndef BOOST_CONFIG_HPP
|
Chris@102
|
17 # include <boost/config.hpp>
|
Chris@102
|
18 #endif
|
Chris@102
|
19
|
Chris@102
|
20 #if defined(BOOST_HAS_PRAGMA_ONCE)
|
Chris@102
|
21 # pragma once
|
Chris@102
|
22 #endif
|
Chris@102
|
23
|
Chris@102
|
24 #include <boost/config.hpp>
|
Chris@102
|
25 #include <boost/core/no_exceptions_support.hpp>
|
Chris@102
|
26
|
Chris@102
|
27 namespace boost {
|
Chris@102
|
28 namespace intrusive {
|
Chris@102
|
29 namespace detail {
|
Chris@102
|
30
|
Chris@102
|
31 //This is not standard, but should work with all compilers
|
Chris@102
|
32 union max_align
|
Chris@102
|
33 {
|
Chris@102
|
34 char char_;
|
Chris@102
|
35 short short_;
|
Chris@102
|
36 int int_;
|
Chris@102
|
37 long long_;
|
Chris@102
|
38 #ifdef BOOST_HAS_LONG_LONG
|
Chris@102
|
39 ::boost::long_long_type long_long_;
|
Chris@102
|
40 #endif
|
Chris@102
|
41 float float_;
|
Chris@102
|
42 double double_;
|
Chris@102
|
43 long double long_double_;
|
Chris@102
|
44 void * void_ptr_;
|
Chris@102
|
45 };
|
Chris@102
|
46
|
Chris@102
|
47 template<class T, std::size_t N>
|
Chris@102
|
48 class array_initializer
|
Chris@102
|
49 {
|
Chris@102
|
50 public:
|
Chris@102
|
51 template<class CommonInitializer>
|
Chris@102
|
52 array_initializer(const CommonInitializer &init)
|
Chris@102
|
53 {
|
Chris@102
|
54 char *init_buf = (char*)rawbuf;
|
Chris@102
|
55 std::size_t i = 0;
|
Chris@102
|
56 BOOST_TRY{
|
Chris@102
|
57 for(; i != N; ++i){
|
Chris@102
|
58 new(init_buf)T(init);
|
Chris@102
|
59 init_buf += sizeof(T);
|
Chris@102
|
60 }
|
Chris@102
|
61 }
|
Chris@102
|
62 BOOST_CATCH(...){
|
Chris@102
|
63 while(i--){
|
Chris@102
|
64 init_buf -= sizeof(T);
|
Chris@102
|
65 ((T*)init_buf)->~T();
|
Chris@102
|
66 }
|
Chris@102
|
67 BOOST_RETHROW;
|
Chris@102
|
68 }
|
Chris@102
|
69 BOOST_CATCH_END
|
Chris@102
|
70 }
|
Chris@102
|
71
|
Chris@102
|
72 operator T* ()
|
Chris@102
|
73 { return (T*)(rawbuf); }
|
Chris@102
|
74
|
Chris@102
|
75 operator const T*() const
|
Chris@102
|
76 { return (const T*)(rawbuf); }
|
Chris@102
|
77
|
Chris@102
|
78 ~array_initializer()
|
Chris@102
|
79 {
|
Chris@102
|
80 char *init_buf = (char*)rawbuf + N*sizeof(T);
|
Chris@102
|
81 for(std::size_t i = 0; i != N; ++i){
|
Chris@102
|
82 init_buf -= sizeof(T);
|
Chris@102
|
83 ((T*)init_buf)->~T();
|
Chris@102
|
84 }
|
Chris@102
|
85 }
|
Chris@102
|
86
|
Chris@102
|
87 private:
|
Chris@102
|
88 detail::max_align rawbuf[(N*sizeof(T)-1)/sizeof(detail::max_align)+1];
|
Chris@102
|
89 };
|
Chris@102
|
90
|
Chris@102
|
91 } //namespace detail{
|
Chris@102
|
92 } //namespace intrusive{
|
Chris@102
|
93 } //namespace boost{
|
Chris@102
|
94
|
Chris@102
|
95 #endif //BOOST_INTRUSIVE_DETAIL_ARRAY_INITIALIZER_HPP
|