]> git.proxmox.com Git - ceph.git/blob - ceph/src/boost/boost/qvm/detail/swizzle_traits.hpp
import new upstream nautilus stable release 14.2.8
[ceph.git] / ceph / src / boost / boost / qvm / detail / swizzle_traits.hpp
1 //Copyright (c) 2008-2016 Emil Dotchevski and Reverge Studios, Inc.
2
3 //Distributed under the Boost Software License, Version 1.0. (See accompanying
4 //file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
5
6 #ifndef UUID_E831FAD6B38F11DE8CECBF0D56D89593
7 #define UUID_E831FAD6B38F11DE8CECBF0D56D89593
8
9 #include <boost/qvm/inline.hpp>
10 #include <boost/qvm/deduce_vec.hpp>
11 #include <boost/qvm/enable_if.hpp>
12 #include <boost/qvm/assert.hpp>
13
14 namespace
15 boost
16 {
17 namespace
18 qvm
19 {
20 namespace
21 qvm_detail
22 {
23 BOOST_QVM_INLINE_CRITICAL
24 void const *
25 get_null()
26 {
27 static int const obj=0;
28 return &obj;
29 }
30
31 template <int A,class Next=void> struct swizzle_idx { static int const value=A; typedef Next next; };
32
33 template <class V,int Idx>
34 struct
35 const_value
36 {
37 static
38 BOOST_QVM_INLINE_TRIVIAL
39 typename vec_traits<V>::scalar_type
40 value()
41 {
42 BOOST_QVM_ASSERT(0);
43 return typename vec_traits<V>::scalar_type();
44 }
45 };
46
47 template <class V>
48 struct
49 const_value<V,-1>
50 {
51 static
52 BOOST_QVM_INLINE_TRIVIAL
53 typename vec_traits<V>::scalar_type
54 value()
55 {
56 return scalar_traits<typename vec_traits<V>::scalar_type>::value(0);
57 }
58 };
59
60 template <class V>
61 struct
62 const_value<V,-2>
63 {
64 static
65 BOOST_QVM_INLINE_TRIVIAL
66 typename vec_traits<V>::scalar_type
67 value()
68 {
69 return scalar_traits<typename vec_traits<V>::scalar_type>::value(1);
70 }
71 };
72
73 template <int Index,bool Neg=(Index<0)>
74 struct neg_zero;
75
76 template <int Index>
77 struct
78 neg_zero<Index,true>
79 {
80 static int const value=0;
81 };
82
83 template <int Index>
84 struct
85 neg_zero<Index,false>
86 {
87 static int const value=Index;
88 };
89
90 template <class SwizzleList,int Index,int C=0>
91 struct
92 swizzle
93 {
94 static int const value=swizzle<typename SwizzleList::next,Index,C+1>::value;
95 };
96
97 template <class SwizzleList,int Match>
98 struct
99 swizzle<SwizzleList,Match,Match>
100 {
101 static int const value=SwizzleList::value;
102 };
103
104 template <int Index,int C>
105 struct swizzle<void,Index,C>;
106
107 template <class SwizzleList,int C=0>
108 struct
109 swizzle_list_length
110 {
111 static int const value=swizzle_list_length<typename SwizzleList::next,C+1>::value;
112 };
113
114 template <int C>
115 struct
116 swizzle_list_length<void,C>
117 {
118 static int const value=C;
119 };
120
121 template <class SwizzleList,int D>
122 struct
123 validate_swizzle_list
124 {
125 static bool const value =
126 ((SwizzleList::value)<D) && //don't touch extra (), MSVC parsing bug.
127 validate_swizzle_list<typename SwizzleList::next,D>::value;
128 };
129
130 template <int D>
131 struct
132 validate_swizzle_list<void,D>
133 {
134 static bool const value=true;
135 };
136
137 template <class OriginalType,class SwizzleList>
138 class
139 sw_
140 {
141 sw_( sw_ const & );
142 sw_ & operator=( sw_ const & );
143 ~sw_();
144
145 BOOST_QVM_STATIC_ASSERT((validate_swizzle_list<SwizzleList,vec_traits<OriginalType>::dim>::value));
146
147 public:
148
149 template <class T>
150 BOOST_QVM_INLINE_TRIVIAL
151 sw_ &
152 operator=( T const & x )
153 {
154 assign(*this,x);
155 return *this;
156 }
157
158 template <class R>
159 BOOST_QVM_INLINE_TRIVIAL
160 operator R() const
161 {
162 R r;
163 assign(r,*this);
164 return r;
165 }
166 };
167
168 template <class SwizzleList>
169 class
170 sw01_
171 {
172 sw01_( sw01_ const & );
173 sw01_ & operator=( sw01_ const & );
174 ~sw01_();
175
176 public:
177
178 template <class R>
179 BOOST_QVM_INLINE_TRIVIAL
180 operator R() const
181 {
182 R r;
183 assign(r,*this);
184 return r;
185 }
186 };
187
188 template <class OriginalType,class SwizzleList>
189 class
190 sws_
191 {
192 sws_( sws_ const & );
193 sws_ & operator=( sws_ const & );
194 ~sws_();
195
196 BOOST_QVM_STATIC_ASSERT((validate_swizzle_list<SwizzleList,1>::value));
197
198 public:
199
200 template <class R>
201 BOOST_QVM_INLINE_TRIVIAL
202 operator R() const
203 {
204 R r;
205 assign(r,*this);
206 return r;
207 }
208 };
209 }
210
211 template <class OriginalVector,class SwizzleList>
212 struct
213 vec_traits<qvm_detail::sw_<OriginalVector,SwizzleList> >
214 {
215 typedef qvm_detail::sw_<OriginalVector,SwizzleList> this_vector;
216 typedef typename vec_traits<OriginalVector>::scalar_type scalar_type;
217 static int const dim=qvm_detail::swizzle_list_length<SwizzleList>::value;
218
219 template <int I>
220 static
221 BOOST_QVM_INLINE_CRITICAL
222 scalar_type
223 read_element( this_vector const & x )
224 {
225 BOOST_QVM_STATIC_ASSERT(I>=0);
226 BOOST_QVM_STATIC_ASSERT(I<dim);
227 int const idx=qvm_detail::swizzle<SwizzleList,I>::value;
228 BOOST_QVM_STATIC_ASSERT(idx<vec_traits<OriginalVector>::dim);
229 return idx>=0?
230 vec_traits<OriginalVector>::template read_element<qvm_detail::neg_zero<idx>::value>(reinterpret_cast<OriginalVector const &>(x)) :
231 qvm_detail::const_value<this_vector,idx>::value();
232 }
233
234 template <int I>
235 static
236 BOOST_QVM_INLINE_CRITICAL
237 scalar_type &
238 write_element( this_vector & x )
239 {
240 BOOST_QVM_STATIC_ASSERT(I>=0);
241 BOOST_QVM_STATIC_ASSERT(I<dim);
242 int const idx=qvm_detail::swizzle<SwizzleList,I>::value;
243 BOOST_QVM_STATIC_ASSERT(idx>=0);
244 BOOST_QVM_STATIC_ASSERT(idx<vec_traits<OriginalVector>::dim);
245 return vec_traits<OriginalVector>::template write_element<idx>(reinterpret_cast<OriginalVector &>(x));
246 }
247 };
248
249 template <class SwizzleList>
250 struct
251 vec_traits<qvm_detail::sw01_<SwizzleList> >
252 {
253 typedef qvm_detail::sw01_<SwizzleList> this_vector;
254 typedef int scalar_type;
255 static int const dim=qvm_detail::swizzle_list_length<SwizzleList>::value;
256
257 template <int I>
258 static
259 BOOST_QVM_INLINE_CRITICAL
260 scalar_type
261 read_element( this_vector const & )
262 {
263 BOOST_QVM_STATIC_ASSERT(I>=0);
264 BOOST_QVM_STATIC_ASSERT(I<dim);
265 int const idx=qvm_detail::swizzle<SwizzleList,I>::value;
266 BOOST_QVM_STATIC_ASSERT(idx<0);
267 return qvm_detail::const_value<this_vector,idx>::value();
268 }
269 };
270
271 template <class OriginalScalar,class SwizzleList>
272 struct
273 vec_traits<qvm_detail::sws_<OriginalScalar,SwizzleList> >
274 {
275 typedef qvm_detail::sws_<OriginalScalar,SwizzleList> this_vector;
276 typedef OriginalScalar scalar_type;
277 static int const dim=qvm_detail::swizzle_list_length<SwizzleList>::value;
278
279 template <int I>
280 static
281 BOOST_QVM_INLINE_CRITICAL
282 scalar_type
283 read_element( this_vector const & x )
284 {
285 BOOST_QVM_STATIC_ASSERT(I>=0);
286 BOOST_QVM_STATIC_ASSERT(I<dim);
287 int const idx=qvm_detail::swizzle<SwizzleList,I>::value;
288 BOOST_QVM_STATIC_ASSERT(idx<1);
289 return idx==0?
290 reinterpret_cast<OriginalScalar const &>(x) :
291 qvm_detail::const_value<this_vector,idx>::value();
292 }
293
294 template <int I>
295 static
296 BOOST_QVM_INLINE_CRITICAL
297 scalar_type &
298 write_element( this_vector & x )
299 {
300 BOOST_QVM_STATIC_ASSERT(I>=0);
301 BOOST_QVM_STATIC_ASSERT(I<dim);
302 int const idx=qvm_detail::swizzle<SwizzleList,I>::value;
303 BOOST_QVM_STATIC_ASSERT(idx==0);
304 return reinterpret_cast<OriginalScalar &>(x);
305 }
306 };
307
308 template <class OriginalVector,class SwizzleList,int D>
309 struct
310 deduce_vec<qvm_detail::sw_<OriginalVector,SwizzleList>,D>
311 {
312 typedef vec<typename vec_traits<OriginalVector>::scalar_type,D> type;
313 };
314
315 template <class OriginalVector,class SwizzleList,int D>
316 struct
317 deduce_vec2<qvm_detail::sw_<OriginalVector,SwizzleList>,qvm_detail::sw_<OriginalVector,SwizzleList>,D>
318 {
319 typedef vec<typename vec_traits<OriginalVector>::scalar_type,D> type;
320 };
321
322 template <class Scalar,class SwizzleList,int D>
323 struct
324 deduce_vec<qvm_detail::sws_<Scalar,SwizzleList>,D>
325 {
326 typedef vec<Scalar,D> type;
327 };
328
329 template <class Scalar,class SwizzleList,int D>
330 struct
331 deduce_vec2<qvm_detail::sws_<Scalar,SwizzleList>,qvm_detail::sws_<Scalar,SwizzleList>,D>
332 {
333 typedef vec<Scalar,D> type;
334 };
335 }
336 }
337
338 #endif