Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(423)

Side by Side Diff: src/core/SkCordic.cpp

Issue 113873008: remove unused SkFixed and SkFract functions (Closed) Base URL: https://skia.googlecode.com/svn/trunk
Patch Set: Created 7 years ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch | Annotate | Revision Log
OLDNEW
(Empty)
1 /*
2 * Copyright 2006 The Android Open Source Project
3 *
4 * Use of this source code is governed by a BSD-style license that can be
5 * found in the LICENSE file.
6 */
7
8 #include "SkCordic.h"
9 #include "SkMathPriv.h"
10 #include "Sk64.h"
11
12 // 0x20000000 equals pi / 4
13 const int32_t kATanDegrees[] = { 0x20000000,
14 0x12E4051D, 0x9FB385B, 0x51111D4, 0x28B0D43, 0x145D7E1, 0xA2F61E, 0x517C55,
15 0x28BE53, 0x145F2E, 0xA2F98, 0x517CC, 0x28BE6, 0x145F3, 0xA2F9, 0x517C,
16 0x28BE, 0x145F, 0xA2F, 0x517, 0x28B, 0x145, 0xA2, 0x51, 0x28, 0x14,
17 0xA, 0x5, 0x2, 0x1 };
18
19 const int32_t kFixedInvGain1 = 0x18bde0bb; // 0.607252935
20
21 static void SkCircularRotation(int32_t* x0, int32_t* y0, int32_t* z0)
22 {
23 int32_t t = 0;
24 int32_t x = *x0;
25 int32_t y = *y0;
26 int32_t z = *z0;
27 const int32_t* tanPtr = kATanDegrees;
28 do {
29 int32_t x1 = y >> t;
30 int32_t y1 = x >> t;
31 int32_t tan = *tanPtr++;
32 if (z >= 0) {
33 x -= x1;
34 y += y1;
35 z -= tan;
36 } else {
37 x += x1;
38 y -= y1;
39 z += tan;
40 }
41 } while (++t < 16); // 30);
42 *x0 = x;
43 *y0 = y;
44 *z0 = z;
45 }
46
47 SkFixed SkCordicSinCos(SkFixed radians, SkFixed* cosp)
48 {
49 int32_t scaledRadians = radians * 0x28be; // scale radians to 65536 / PI()
50 int quadrant = scaledRadians >> 30;
51 quadrant += 1;
52 if (quadrant & 2)
53 scaledRadians = -scaledRadians + 0x80000000;
54 /* |a| <= 90 degrees as a 1.31 number */
55 SkFixed sin = 0;
56 SkFixed cos = kFixedInvGain1;
57 SkCircularRotation(&cos, &sin, &scaledRadians);
58 Sk64 scaled;
59 scaled.setMul(sin, 0x6488d);
60 sin = scaled.fHi;
61 scaled.setMul(cos, 0x6488d);
62 if (quadrant & 2)
63 scaled.fHi = - scaled.fHi;
64 *cosp = scaled.fHi;
65 return sin;
66 }
67
68 SkFixed SkCordicTan(SkFixed a)
69 {
70 int32_t cos;
71 int32_t sin = SkCordicSinCos(a, &cos);
72 return SkFixedDiv(sin, cos);
73 }
74
75 static int32_t SkCircularVector(int32_t* y0, int32_t* x0, int32_t vecMode)
76 {
77 int32_t x = *x0;
78 int32_t y = *y0;
79 int32_t z = 0;
80 int32_t t = 0;
81 const int32_t* tanPtr = kATanDegrees;
82 do {
83 int32_t x1 = y >> t;
84 int32_t y1 = x >> t;
85 int32_t tan = *tanPtr++;
86 if (y < vecMode) {
87 x -= x1;
88 y += y1;
89 z -= tan;
90 } else {
91 x += x1;
92 y -= y1;
93 z += tan;
94 }
95 } while (++t < 16); // 30
96 Sk64 scaled;
97 scaled.setMul(z, 0x6488d); // scale back into the SkScalar space (0x10000000 0/0x28be)
98 return scaled.fHi;
99 }
100
101 SkFixed SkCordicASin(SkFixed a) {
102 int32_t sign = SkExtractSign(a);
103 int32_t z = SkFixedAbs(a);
104 if (z >= SK_Fixed1)
105 return SkApplySign(SK_FixedPI>>1, sign);
106 int32_t x = kFixedInvGain1;
107 int32_t y = 0;
108 z *= 0x28be;
109 z = SkCircularVector(&y, &x, z);
110 z = SkApplySign(z, ~sign);
111 return z;
112 }
113
114 SkFixed SkCordicACos(SkFixed a) {
115 int32_t z = SkCordicASin(a);
116 z = (SK_FixedPI>>1) - z;
117 return z;
118 }
119
120 SkFixed SkCordicATan2(SkFixed y, SkFixed x) {
121 if ((x | y) == 0)
122 return 0;
123 int32_t xsign = SkExtractSign(x);
124 x = SkFixedAbs(x);
125 int32_t result = SkCircularVector(&y, &x, 0);
126 if (xsign) {
127 int32_t rsign = SkExtractSign(result);
128 if (y == 0)
129 rsign = 0;
130 SkFixed pi = SkApplySign(SK_FixedPI, rsign);
131 result = pi - result;
132 }
133 return result;
134 }
135
136 const int32_t kATanHDegrees[] = {
137 0x1661788D, 0xA680D61, 0x51EA6FC, 0x28CBFDD, 0x1460E34,
138 0xA2FCE8, 0x517D2E, 0x28BE6E, 0x145F32,
139 0xA2F98, 0x517CC, 0x28BE6, 0x145F3, 0xA2F9, 0x517C,
140 0x28BE, 0x145F, 0xA2F, 0x517, 0x28B, 0x145, 0xA2, 0x51, 0x28, 0x14,
141 0xA, 0x5, 0x2, 0x1 };
142
143 const int32_t kFixedInvGain2 = 0x31330AAA; // 1.207534495
144
145 static void SkHyperbolic(int32_t* x0, int32_t* y0, int32_t* z0, int mode)
146 {
147 int32_t t = 1;
148 int32_t x = *x0;
149 int32_t y = *y0;
150 int32_t z = *z0;
151 const int32_t* tanPtr = kATanHDegrees;
152 int k = -3;
153 do {
154 int32_t x1 = y >> t;
155 int32_t y1 = x >> t;
156 int32_t tan = *tanPtr++;
157 int count = 2 + (k >> 31);
158 if (++k == 1)
159 k = -2;
160 do {
161 if (((y >> 31) & mode) | ~((z >> 31) | mode)) {
162 x += x1;
163 y += y1;
164 z -= tan;
165 } else {
166 x -= x1;
167 y -= y1;
168 z += tan;
169 }
170 } while (--count);
171 } while (++t < 30);
172 *x0 = x;
173 *y0 = y;
174 *z0 = z;
175 }
176
177 SkFixed SkCordicLog(SkFixed a) {
178 a *= 0x28be;
179 int32_t x = a + 0x28BE60DB; // 1.0
180 int32_t y = a - 0x28BE60DB;
181 int32_t z = 0;
182 SkHyperbolic(&x, &y, &z, -1);
183 Sk64 scaled;
184 scaled.setMul(z, 0x6488d);
185 z = scaled.fHi;
186 return z << 1;
187 }
188
189 SkFixed SkCordicExp(SkFixed a) {
190 int32_t cosh = kFixedInvGain2;
191 int32_t sinh = 0;
192 SkHyperbolic(&cosh, &sinh, &a, 0);
193 return cosh + sinh;
194 }
195
196 #ifdef SK_DEBUG
197
198 #include "SkFloatingPoint.h"
199
200 void SkCordic_UnitTest()
201 {
202 #if defined(SK_SUPPORT_UNITTEST)
203 float val;
204 for (float angle = -720; angle < 720; angle += 30) {
205 float radian = angle * 3.1415925358f / 180.0f;
206 SkFixed f_angle = SkFloatToFixed(radian);
207 // sincos
208 float sine = sinf(radian);
209 float cosine = cosf(radian);
210 SkFixed f_cosine;
211 SkFixed f_sine = SkCordicSinCos(f_angle, &f_cosine);
212 float sine2 = (float) f_sine / 65536.0f;
213 float cosine2 = (float) f_cosine / 65536.0f;
214 float error = fabsf(sine - sine2);
215 if (error > 0.001)
216 SkDebugf("sin error : angle = %g ; sin = %g ; cordic = %g\n", angle, sine, sine2);
217 error = fabsf(cosine - cosine2);
218 if (error > 0.001)
219 SkDebugf("cos error : angle = %g ; cos = %g ; cordic = %g\n", angle, cosine, cosine2);
220 // tan
221 float _tan = tanf(radian);
222 SkFixed f_tan = SkCordicTan(f_angle);
223 float tan2 = (float) f_tan / 65536.0f;
224 error = fabsf(_tan - tan2);
225 if (error > 0.05 && fabsf(_tan) < 1e6)
226 SkDebugf("tan error : angle = %g ; tan = %g ; cordic = %g\n", angle, _tan, tan2);
227 }
228 for (val = -1; val <= 1; val += .1f) {
229 SkFixed f_val = SkFloatToFixed(val);
230 // asin
231 float arcsine = asinf(val);
232 SkFixed f_arcsine = SkCordicASin(f_val);
233 float arcsine2 = (float) f_arcsine / 65536.0f;
234 float error = fabsf(arcsine - arcsine2);
235 if (error > 0.001)
236 SkDebugf("asin error : val = %g ; asin = %g ; cordic = %g\n", val, a rcsine, arcsine2);
237 }
238 #if 1
239 for (val = -1; val <= 1; val += .1f) {
240 #else
241 val = .5; {
242 #endif
243 SkFixed f_val = SkFloatToFixed(val);
244 // acos
245 float arccos = acosf(val);
246 SkFixed f_arccos = SkCordicACos(f_val);
247 float arccos2 = (float) f_arccos / 65536.0f;
248 float error = fabsf(arccos - arccos2);
249 if (error > 0.001)
250 SkDebugf("acos error : val = %g ; acos = %g ; cordic = %g\n", val, a rccos, arccos2);
251 }
252 // atan2
253 #if 1
254 for (val = -1000; val <= 1000; val += 500.f) {
255 for (float val2 = -1000; val2 <= 1000; val2 += 500.f) {
256 #else
257 val = 0; {
258 float val2 = -1000; {
259 #endif
260 SkFixed f_val = SkFloatToFixed(val);
261 SkFixed f_val2 = SkFloatToFixed(val2);
262 float arctan = atan2f(val, val2);
263 SkFixed f_arctan = SkCordicATan2(f_val, f_val2);
264 float arctan2 = (float) f_arctan / 65536.0f;
265 float error = fabsf(arctan - arctan2);
266 if (error > 0.001)
267 SkDebugf("atan2 error : val = %g ; val2 = %g ; atan2 = %g ; cord ic = %g\n", val, val2, arctan, arctan2);
268 }
269 }
270 // log
271 #if 1
272 for (val = 0.125f; val <= 8.f; val *= 2.0f) {
273 #else
274 val = .5; {
275 #endif
276 SkFixed f_val = SkFloatToFixed(val);
277 // acos
278 float log = logf(val);
279 SkFixed f_log = SkCordicLog(f_val);
280 float log2 = (float) f_log / 65536.0f;
281 float error = fabsf(log - log2);
282 if (error > 0.001)
283 SkDebugf("log error : val = %g ; log = %g ; cordic = %g\n", val, log , log2);
284 }
285 // exp
286 #endif
287 }
288
289 #endif
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698