1/*
2 * @APPLE_LICENSE_HEADER_START@
3 *
4 * Copyright (c) 1999-2010 Apple Computer, Inc.  All Rights Reserved.
5 *
6 * This file contains Original Code and/or Modifications of Original Code
7 * as defined in and that are subject to the Apple Public Source License
8 * Version 2.0 (the 'License'). You may not use this file except in
9 * compliance with the License. Please obtain a copy of the License at
10 * http://www.opensource.apple.com/apsl/ and read it before using this
11 * file.
12 *
13 * The Original Code and all software distributed under the License are
14 * distributed on an 'AS IS' basis, WITHOUT WARRANTY OF ANY KIND, EITHER
15 * EXPRESS OR IMPLIED, AND APPLE HEREBY DISCLAIMS ALL SUCH WARRANTIES,
16 * INCLUDING WITHOUT LIMITATION, ANY WARRANTIES OF MERCHANTABILITY,
17 * FITNESS FOR A PARTICULAR PURPOSE, QUIET ENJOYMENT OR NON-INFRINGEMENT.
18 * Please see the License for the specific language governing rights and
19 * limitations under the License.
20 *
21 * @APPLE_LICENSE_HEADER_END@
22 */
23
24#include "IOFixed64.h"
25
26IOFixed64 operator* (const IOFixed64 a, const IOFixed64 b)
27{
28    IOFixed64 result(a);
29    result *= b;
30    return result;
31}
32
33IOFixed64 operator* (const IOFixed64 a, const SInt64 b)
34{
35    IOFixed64 result(a);
36    result *= b;
37    return result;
38}
39
40IOFixed64 operator/ (const IOFixed64 a, const IOFixed64 b)
41{
42    IOFixed64 result(a);
43    result /= b;
44    return result;
45}
46
47IOFixed64 operator/ (const IOFixed64 a, const SInt64 b)
48{
49    IOFixed64 result(a);
50    result /= b;
51    return result;
52}
53
54IOFixed64 operator+ (const IOFixed64 a, const IOFixed64 b)
55{
56    IOFixed64 result(a);
57    result += b;
58    return result;
59}
60
61IOFixed64 operator+ (const IOFixed64 a, const SInt64 b)
62{
63    IOFixed64 result(a);
64    result += b;
65    return result;
66}
67
68IOFixed64 operator- (const IOFixed64 a, const IOFixed64 b)
69{
70    IOFixed64 result(a);
71    result -= b;
72    return result;
73}
74
75IOFixed64 operator- (const IOFixed64 a, const SInt64 b)
76{
77    IOFixed64 result(a);
78    result -= b;
79    return result;
80}
81
82IOFixed64 exponent(const IOFixed64 original, const UInt8 power)
83{
84    IOFixed64 result;
85    if (power) {
86        int i;
87        result = original;
88        for (i = 1; i < power; i++) {
89            result *= original;
90        }
91    }
92    return result;
93}
94
95UInt32 llsqrt(UInt64 x)
96{
97    UInt64 rem = 0;
98    UInt64 root = 0;
99    int i;
100
101    for (i = 0; i < 32; i++) {
102        root <<= 1;
103        rem = ((rem << 2) + (x >> 62));
104        x <<= 2;
105
106        root++;
107
108        if (root <= rem) {
109            rem -=  root;
110            root++;
111        } else {
112            root--;
113        }
114    }
115
116    return(UInt32)(root >> 1);
117}
118
119UInt16 lsqrt(UInt32 x)
120{
121    UInt32 rem = 0;
122    UInt32 root = 0;
123    int i;
124
125    for (i = 0; i < 16; i++) {
126        root <<= 1;
127        rem = ((rem << 2) + (x >> 30));
128        x <<= 2;
129
130        root++;
131
132        if (root <= rem) {
133            rem -=  root;
134            root++;
135        } else {
136            root--;
137        }
138    }
139
140    return(UInt16)(root >> 1);
141}
142
143IOFixed64 IOQuarticFunction( const IOFixed64 x, const IOFixed64 *gains )
144{
145	// Computes hyper-cubic polynomial with 0-intercept: f(x) = m1*x + m2^2 * x^2 + m3^3 * x^3 + m4^4 * x^4
146	IOFixed64 function_at_x = x * gains[0] + exponent(x * gains[1], 2);
147
148	// -- Because of IOFixed overhead, don't bother computing higher expansions unless their gain coefficients are non-zero:
149	if( gains[2] != 0LL )
150		function_at_x += exponent(x * gains[2], 3);
151
152	if( gains[3] != 0LL )
153		function_at_x += exponent(x * gains[3], 4);
154
155	return function_at_x;
156}
157
158IOFixed64 IOQuarticDerivative( const IOFixed64 x, const IOFixed64 *gains )
159{
160	// For hyper-cubic polynomial with 0-intercept: f(x) = m1*x + m2^2 * x^2 + m3^3 * x^3 + m4^4 * x^4
161	// This function evaluates the derivative: f'(x) = m1 + 2 * x * m2^2 + 3 * x^2 * m3^3 + 4 * x^3 * m4^4
162	IOFixed64 derivative_at_x = gains[0] + x * exponent(gains[1], 2) * 2LL;
163
164	// -- Because of IOFixed overhead, don't bother computing higher expansions unless their gain coefficients are non-zero:
165	if( gains[2] != 0LL )
166		derivative_at_x += exponent(x, 2) * exponent(gains[2], 3) * 3LL;
167
168	if( gains[3] != 0LL )
169		derivative_at_x += exponent(x, 3) * exponent(gains[3], 4) * 4LL;
170
171	return derivative_at_x;
172}
173
174