|
1 // |
|
2 // Copyright (c) 2002-2012 The ANGLE Project Authors. All rights reserved. |
|
3 // Use of this source code is governed by a BSD-style license that can be |
|
4 // found in the LICENSE file. |
|
5 // |
|
6 |
|
7 // mathutil.h: Math and bit manipulation functions. |
|
8 |
|
9 #ifndef LIBGLESV2_MATHUTIL_H_ |
|
10 #define LIBGLESV2_MATHUTIL_H_ |
|
11 |
|
12 #include <intrin.h> |
|
13 |
|
14 #include "common/system.h" |
|
15 #include "common/debug.h" |
|
16 |
|
17 namespace gl |
|
18 { |
|
19 struct Vector4 |
|
20 { |
|
21 Vector4() {} |
|
22 Vector4(float x, float y, float z, float w) : x(x), y(y), z(z), w(w) {} |
|
23 |
|
24 float x; |
|
25 float y; |
|
26 float z; |
|
27 float w; |
|
28 }; |
|
29 |
|
30 inline bool isPow2(int x) |
|
31 { |
|
32 return (x & (x - 1)) == 0 && (x != 0); |
|
33 } |
|
34 |
|
35 inline int log2(int x) |
|
36 { |
|
37 int r = 0; |
|
38 while ((x >> r) > 1) r++; |
|
39 return r; |
|
40 } |
|
41 |
|
42 inline unsigned int ceilPow2(unsigned int x) |
|
43 { |
|
44 if (x != 0) x--; |
|
45 x |= x >> 1; |
|
46 x |= x >> 2; |
|
47 x |= x >> 4; |
|
48 x |= x >> 8; |
|
49 x |= x >> 16; |
|
50 x++; |
|
51 |
|
52 return x; |
|
53 } |
|
54 |
|
55 template<typename T, typename MIN, typename MAX> |
|
56 inline T clamp(T x, MIN min, MAX max) |
|
57 { |
|
58 // Since NaNs fail all comparison tests, a NaN value will default to min |
|
59 return x > min ? (x > max ? max : x) : min; |
|
60 } |
|
61 |
|
62 inline float clamp01(float x) |
|
63 { |
|
64 return clamp(x, 0.0f, 1.0f); |
|
65 } |
|
66 |
|
67 template<const int n> |
|
68 inline unsigned int unorm(float x) |
|
69 { |
|
70 const unsigned int max = 0xFFFFFFFF >> (32 - n); |
|
71 |
|
72 if (x > 1) |
|
73 { |
|
74 return max; |
|
75 } |
|
76 else if (x < 0) |
|
77 { |
|
78 return 0; |
|
79 } |
|
80 else |
|
81 { |
|
82 return (unsigned int)(max * x + 0.5f); |
|
83 } |
|
84 } |
|
85 |
|
86 inline bool supportsSSE2() |
|
87 { |
|
88 static bool checked = false; |
|
89 static bool supports = false; |
|
90 |
|
91 if (checked) |
|
92 { |
|
93 return supports; |
|
94 } |
|
95 |
|
96 int info[4]; |
|
97 __cpuid(info, 0); |
|
98 |
|
99 if (info[0] >= 1) |
|
100 { |
|
101 __cpuid(info, 1); |
|
102 |
|
103 supports = (info[3] >> 26) & 1; |
|
104 } |
|
105 |
|
106 checked = true; |
|
107 |
|
108 return supports; |
|
109 } |
|
110 |
|
111 inline unsigned short float32ToFloat16(float fp32) |
|
112 { |
|
113 unsigned int fp32i = (unsigned int&)fp32; |
|
114 unsigned int sign = (fp32i & 0x80000000) >> 16; |
|
115 unsigned int abs = fp32i & 0x7FFFFFFF; |
|
116 |
|
117 if(abs > 0x47FFEFFF) // Infinity |
|
118 { |
|
119 return sign | 0x7FFF; |
|
120 } |
|
121 else if(abs < 0x38800000) // Denormal |
|
122 { |
|
123 unsigned int mantissa = (abs & 0x007FFFFF) | 0x00800000; |
|
124 int e = 113 - (abs >> 23); |
|
125 |
|
126 if(e < 24) |
|
127 { |
|
128 abs = mantissa >> e; |
|
129 } |
|
130 else |
|
131 { |
|
132 abs = 0; |
|
133 } |
|
134 |
|
135 return sign | (abs + 0x00000FFF + ((abs >> 13) & 1)) >> 13; |
|
136 } |
|
137 else |
|
138 { |
|
139 return sign | (abs + 0xC8000000 + 0x00000FFF + ((abs >> 13) & 1)) >> 13; |
|
140 } |
|
141 } |
|
142 |
|
143 float float16ToFloat32(unsigned short h); |
|
144 |
|
145 } |
|
146 |
|
147 namespace rx |
|
148 { |
|
149 |
|
150 struct Range |
|
151 { |
|
152 Range() {} |
|
153 Range(int lo, int hi) : start(lo), end(hi) { ASSERT(lo <= hi); } |
|
154 |
|
155 int start; |
|
156 int end; |
|
157 }; |
|
158 |
|
159 } |
|
160 |
|
161 #endif // LIBGLESV2_MATHUTIL_H_ |