glslang: Fix over 100 warnings from MSVC warning level 4.
[platform/upstream/glslang.git] / glslang / Include / ConstantUnion.h
1 //
2 //Copyright (C) 2002-2005  3Dlabs Inc. Ltd.
3 //Copyright (C) 2013 LunarG, Inc.
4 //
5 //All rights reserved.
6 //
7 //Redistribution and use in source and binary forms, with or without
8 //modification, are permitted provided that the following conditions
9 //are met:
10 //
11 //    Redistributions of source code must retain the above copyright
12 //    notice, this list of conditions and the following disclaimer.
13 //
14 //    Redistributions in binary form must reproduce the above
15 //    copyright notice, this list of conditions and the following
16 //    disclaimer in the documentation and/or other materials provided
17 //    with the distribution.
18 //
19 //    Neither the name of 3Dlabs Inc. Ltd. nor the names of its
20 //    contributors may be used to endorse or promote products derived
21 //    from this software without specific prior written permission.
22 //
23 //THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
24 //"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
25 //LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
26 //FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE
27 //COPYRIGHT HOLDERS OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,
28 //INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
29 //BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
30 //LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
31 //CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
32 //LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN
33 //ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
34 //POSSIBILITY OF SUCH DAMAGE.
35 //
36
37 #ifndef _CONSTANT_UNION_INCLUDED_
38 #define _CONSTANT_UNION_INCLUDED_
39
40 namespace glslang {
41
42 class TConstUnion {
43 public:
44     POOL_ALLOCATOR_NEW_DELETE(GetThreadPoolAllocator())
45
46     void setIConst(int i)
47     { 
48         iConst = i; 
49         type = EbtInt;
50     }
51
52     void setUConst(unsigned int u)
53     {
54         uConst = u; 
55         type = EbtUint;
56     }
57
58     void setDConst(double d)
59     {
60         dConst = d; 
61         type = EbtDouble;
62     }
63
64     void setBConst(bool b)
65     {
66         bConst = b; 
67         type = EbtBool;
68     }
69
70     int getIConst() const          { return iConst; }
71     unsigned int getUConst() const { return uConst; }
72     double getDConst() const       { return dConst; }
73     bool getBConst() const         { return bConst; }
74
75     bool operator==(const int i) const
76     {
77         if (i == iConst)
78             return true;
79
80         return false;
81     }
82
83     bool operator==(unsigned const int u) const
84     {
85         if (u == uConst)
86             return true;
87
88         return false;
89     }
90
91     bool operator==(const double d) const
92     {
93         if (d == dConst)
94             return true;
95
96         return false;
97     }
98
99     bool operator==(const bool b) const
100     {
101         if (b == bConst)
102             return true;
103
104         return false;
105     }
106
107     bool operator==(const TConstUnion& constant) const
108     {
109         if (constant.type != type)
110             return false;
111
112         switch (type) {
113         case EbtInt:
114             if (constant.iConst == iConst)
115                 return true;
116
117             break;
118         case EbtUint:
119             if (constant.uConst == uConst)
120                 return true;
121
122             break;
123         case EbtDouble:
124             if (constant.dConst == dConst)
125                 return true;
126
127             break;
128         case EbtBool:
129             if (constant.bConst == bConst)
130                 return true;
131
132             break;
133         default:
134             assert(false && "Default missing");
135         }
136
137         return false;
138     }
139
140     bool operator!=(const int i) const
141     {
142         return !operator==(i);
143     }
144
145     bool operator!=(const unsigned int u) const
146     {
147         return !operator==(u);
148     }
149
150     bool operator!=(const float f) const
151     {
152         return !operator==(f);
153     }
154
155     bool operator!=(const bool b) const
156     {
157         return !operator==(b);
158     }
159
160     bool operator!=(const TConstUnion& constant) const
161     {
162         return !operator==(constant);
163     }
164
165     bool operator>(const TConstUnion& constant) const
166     { 
167         assert(type == constant.type);
168         switch (type) {
169         case EbtInt:
170             if (iConst > constant.iConst)
171                 return true;
172
173             return false;
174         case EbtUint:
175             if (uConst > constant.uConst)
176                 return true;
177
178             return false;
179         case EbtDouble:
180             if (dConst > constant.dConst)
181                 return true;
182
183             return false;
184         default:
185             assert(false && "Default missing");
186             return false;
187         }
188     }
189
190     bool operator<(const TConstUnion& constant) const
191     { 
192         assert(type == constant.type);
193         switch (type) {
194         case EbtInt:
195             if (iConst < constant.iConst)
196                 return true;
197
198             return false;
199         case EbtUint:
200             if (uConst < constant.uConst)
201                 return true;
202
203             return false;
204         case EbtDouble:
205             if (dConst < constant.dConst)
206                 return true;
207
208             return false;
209         default:
210             assert(false && "Default missing");
211             return false;
212         }
213     }
214
215     TConstUnion operator+(const TConstUnion& constant) const
216     { 
217         TConstUnion returnValue;
218         assert(type == constant.type);
219         switch (type) {
220         case EbtInt: returnValue.setIConst(iConst + constant.iConst); break;
221         case EbtUint: returnValue.setUConst(uConst + constant.uConst); break;
222         case EbtDouble: returnValue.setDConst(dConst + constant.dConst); break;
223         default: assert(false && "Default missing");
224         }
225
226         return returnValue;
227     }
228
229     TConstUnion operator-(const TConstUnion& constant) const
230     { 
231         TConstUnion returnValue;
232         assert(type == constant.type);
233         switch (type) {
234         case EbtInt: returnValue.setIConst(iConst - constant.iConst); break;
235         case EbtUint: returnValue.setUConst(uConst - constant.uConst); break;
236         case EbtDouble: returnValue.setDConst(dConst - constant.dConst); break;
237         default: assert(false && "Default missing");
238         }
239
240         return returnValue;
241     }
242
243     TConstUnion operator*(const TConstUnion& constant) const
244     { 
245         TConstUnion returnValue;
246         assert(type == constant.type);
247         switch (type) {
248         case EbtInt: returnValue.setIConst(iConst * constant.iConst); break;
249         case EbtUint: returnValue.setUConst(uConst * constant.uConst); break;
250         case EbtDouble: returnValue.setDConst(dConst * constant.dConst); break; 
251         default: assert(false && "Default missing");
252         }
253
254         return returnValue;
255     }
256
257     TConstUnion operator%(const TConstUnion& constant) const
258     { 
259         TConstUnion returnValue;
260         assert(type == constant.type);
261         switch (type) {
262         case EbtInt:  returnValue.setIConst(iConst % constant.iConst); break;
263         case EbtUint: returnValue.setUConst(uConst % constant.uConst); break;
264         default:     assert(false && "Default missing");
265         }
266
267         return returnValue;
268     }
269
270     TConstUnion operator>>(const TConstUnion& constant) const
271     { 
272         TConstUnion returnValue;
273         switch (type) {
274         case EbtInt:
275             switch (constant.type) {
276             case EbtInt:   returnValue.setIConst(iConst >> constant.iConst); break;
277             case EbtUint:  returnValue.setIConst(iConst >> constant.uConst); break;
278             default:       assert(false && "Default missing");           
279             }
280             break;
281         case EbtUint:
282             switch (constant.type) {
283             case EbtInt:   returnValue.setUConst(uConst >> constant.iConst); break;
284             case EbtUint:  returnValue.setUConst(uConst >> constant.uConst); break;
285             default:       assert(false && "Default missing");           
286             }
287             break;
288         default:     assert(false && "Default missing");
289         }
290
291         return returnValue;
292     }
293
294     TConstUnion operator<<(const TConstUnion& constant) const
295     { 
296         TConstUnion returnValue;
297         switch (type) {
298         case EbtInt:
299             switch (constant.type) {
300             case EbtInt:   returnValue.setIConst(iConst << constant.iConst); break;
301             case EbtUint:  returnValue.setIConst(iConst << constant.uConst); break;
302             default:       assert(false && "Default missing");           
303             }
304             break;
305         case EbtUint:
306             switch (constant.type) {
307             case EbtInt:   returnValue.setUConst(uConst << constant.iConst); break;
308             case EbtUint:  returnValue.setUConst(uConst << constant.uConst); break;
309             default:       assert(false && "Default missing");           
310             }
311             break;
312         default:     assert(false && "Default missing");
313         }
314
315         return returnValue;
316     }
317
318     TConstUnion operator&(const TConstUnion& constant) const
319     { 
320         TConstUnion returnValue;
321         assert(type == constant.type);
322         switch (type) {
323         case EbtInt:  returnValue.setIConst(iConst & constant.iConst); break;
324         case EbtUint: returnValue.setUConst(uConst & constant.uConst); break;
325         default:     assert(false && "Default missing");
326         }
327
328         return returnValue;
329     }
330
331     TConstUnion operator|(const TConstUnion& constant) const
332     { 
333         TConstUnion returnValue;
334         assert(type == constant.type);
335         switch (type) {
336         case EbtInt:  returnValue.setIConst(iConst | constant.iConst); break;
337         case EbtUint: returnValue.setUConst(uConst | constant.uConst); break;
338         default:     assert(false && "Default missing");
339         }
340
341         return returnValue;
342     }
343
344     TConstUnion operator^(const TConstUnion& constant) const
345     { 
346         TConstUnion returnValue;
347         assert(type == constant.type);
348         switch (type) {
349         case EbtInt:  returnValue.setIConst(iConst ^ constant.iConst); break;
350         case EbtUint: returnValue.setUConst(uConst ^ constant.uConst); break;
351         default:     assert(false && "Default missing");
352         }
353
354         return returnValue;
355     }
356
357     TConstUnion operator~() const
358     { 
359         TConstUnion returnValue;
360         switch (type) {
361         case EbtInt:  returnValue.setIConst(~iConst); break;
362         case EbtUint: returnValue.setUConst(~uConst); break;
363         default:     assert(false && "Default missing");
364         }
365
366         return returnValue;
367     }
368
369     TConstUnion operator&&(const TConstUnion& constant) const
370     { 
371         TConstUnion returnValue;
372         assert(type == constant.type);
373         switch (type) {
374         case EbtBool: returnValue.setBConst(bConst && constant.bConst); break;
375         default:     assert(false && "Default missing");
376         }
377
378         return returnValue;
379     }
380
381     TConstUnion operator||(const TConstUnion& constant) const
382     { 
383         TConstUnion returnValue;
384         assert(type == constant.type);
385         switch (type) {
386         case EbtBool: returnValue.setBConst(bConst || constant.bConst); break;
387         default:     assert(false && "Default missing");
388         }
389
390         return returnValue;
391     }
392
393     TBasicType getType() const { return type; }
394
395 private:
396     union  {
397         int iConst;          // used for ivec, scalar ints
398         unsigned int uConst; // used for uvec, scalar uints
399         bool bConst;         // used for bvec, scalar bools
400         double dConst;       // used for vec, dvec, mat, dmat, scalar floats and doubles
401     } ;
402
403     TBasicType type;
404 };
405
406 // Encapsulate having a pointer to an array of TConstUnion,
407 // which only needs to be allocated if it's size is going to be
408 // bigger than 0.
409 //
410 // One convenience is being able to use [] to go inside the array, instead
411 // of C++ assuming it as an array of pointers to vectors.
412 //
413 // General usage is that the size is known up front, and it is 
414 // created once with the proper size.
415 //
416 class TConstUnionArray {
417 public:
418     POOL_ALLOCATOR_NEW_DELETE(GetThreadPoolAllocator())
419
420     TConstUnionArray() : unionArray(0) { }
421     virtual ~TConstUnionArray() { }
422
423     explicit TConstUnionArray(int size)
424     {
425         if (size == 0)
426             unionArray = 0;
427         else
428             unionArray =  new TConstUnionVector(size);
429     }
430     TConstUnionArray(const TConstUnionArray& a) : unionArray(a.unionArray) { }
431     TConstUnionArray(const TConstUnionArray& a, int start, int size)
432     {
433         unionArray = new TConstUnionVector(size);
434         for (int i = 0; i < size; ++i)
435             (*unionArray)[i] = a[start + i];
436     }
437
438     // Use this constructor for a smear operation
439     TConstUnionArray(int size, const TConstUnion& val)
440     {
441         unionArray = new TConstUnionVector(size, val);
442     }
443
444     int size() const { return unionArray ? (int)unionArray->size() : 0; }
445     TConstUnion& operator[](size_t index) { return (*unionArray)[index]; }
446     const TConstUnion& operator[](size_t index) const { return (*unionArray)[index]; }
447     bool operator==(const TConstUnionArray& rhs) const
448     {
449         // this includes the case that both are unallocated
450         if (unionArray == rhs.unionArray)
451             return true;
452
453         if (! unionArray || ! rhs.unionArray)
454             return false;
455
456         if (! unionArray || ! rhs.unionArray)
457             return false;
458
459         return *unionArray == *rhs.unionArray;
460     }
461     bool operator!=(const TConstUnionArray& rhs) const { return ! operator==(rhs); }
462
463     double dot(const TConstUnionArray& rhs)
464     {
465         assert(rhs.unionArray->size() == unionArray->size());
466         double sum = 0.0;
467
468         for (size_t comp = 0; comp < unionArray->size(); ++comp)
469             sum += (*this)[comp].getDConst() * rhs[comp].getDConst();
470
471         return sum;
472     }
473
474     bool empty() const { return unionArray == 0; }
475
476 protected:
477     typedef TVector<TConstUnion> TConstUnionVector;
478     TConstUnionVector* unionArray;
479 };
480
481 } // end namespace glslang
482
483 #endif // _CONSTANT_UNION_INCLUDED_