KallistiOS  2.0.0
 All Data Structures Files Functions Variables Typedefs Enumerations Enumerator Macros Groups
fmath.h
Go to the documentation of this file.
1 /* KallistiOS 2.0.0
2 
3  dc/fmath.h
4  (C)2001 Andrew Kieschnick
5 
6 */
7 
8 #ifndef __DC_FMATH_H
9 #define __DC_FMATH_H
10 
11 #include <sys/cdefs.h>
12 __BEGIN_DECLS
13 
14 #include <arch/types.h>
15 
16 /**
17  \file dc/fmath.h
18  \brief Inline functions for the DC's special math instructions
19  \author Andrew Kieschnick
20 */
21 
22 /** PI constant (if you don't want full math.h) */
23 #define F_PI 3.1415926f
24 
25 /** \cond */
26 #define __fsin(x) \
27  ({ float __value, __arg = (x), __scale = 10430.37835; \
28  asm( "fmul %2,%1\n\t" \
29  "ftrc %1,fpul\n\t" \
30  "fsca fpul,dr0\n\t" \
31  "fmov fr0,%0" \
32  : "=f" (__value), "+&f" (__scale) \
33  : "f" (__arg) \
34  : "fpul", "fr0", "fr1"); \
35  __value; })
36 
37 #define __fcos(x) \
38  ({ float __value, __arg = (x), __scale = 10430.37835; \
39  asm( "fmul %2,%1\n\t" \
40  "ftrc %1,fpul\n\t" \
41  "fsca fpul,dr0\n\t" \
42  "fmov fr1,%0" \
43  : "=f" (__value), "+&f" (__scale) \
44  : "f" (__arg) \
45  : "fpul", "fr0", "fr1"); \
46  __value; })
47 
48 #define __ftan(x) \
49  ({ float __value, __arg = (x), __scale = 10430.37835; \
50  asm( "fmul %2,%1\n\t" \
51  "ftrc %1,fpul\n\t" \
52  "fsca fpul,dr0\n\t" \
53  "fdiv fr1, fr0\n\t" \
54  "fmov fr0,%0" \
55  : "=f" (__value), "+&f" (__scale) \
56  : "f" (__arg) \
57  : "fpul", "fr0", "fr1"); \
58  __value; })
59 
60 
61 #define __fisin(x) \
62  ({ float __value, __arg = (x); \
63  asm( "lds %1,fpul\n\t" \
64  "fsca fpul,dr0\n\t" \
65  "fmov fr0,%0" \
66  : "=f" (__value) \
67  : "r" (__arg) \
68  : "fpul", "fr0", "fr1"); \
69  __value; })
70 
71 #define __ficos(x) \
72  ({ float __value, __arg = (x); \
73  asm( "lds %1,fpul\n\t" \
74  "fsca fpul,dr0\n\t" \
75  "fmov fr1,%0" \
76  : "=f" (__value) \
77  : "r" (__arg) \
78  : "fpul", "fr0", "fr1"); \
79  __value; })
80 
81 #define __fitan(x) \
82  ({ float __value, __arg = (x); \
83  asm( "lds %1,fpul\n\t" \
84  "fsca fpul,dr0\n\t" \
85  "fdiv fr1, fr0\n\t" \
86  "fmov fr0,%0" \
87  : "=f" (__value) \
88  : "r" (__arg) \
89  : "fpul", "fr0", "fr1"); \
90  __value; })
91 
92 
93 #define __fsqrt(x) \
94  ({ float __arg = (x); \
95  asm( "fsqrt %0\n\t" \
96  : "=f" (__arg) : "0" (__arg)); \
97  __arg; })
98 
99 #define __frsqrt(x) \
100  ({ float __arg = (x); \
101  asm( "fsrra %0\n\t" \
102  : "=f" (__arg) : "0" (__arg)); \
103  __arg; })
104 
105 /* Floating point inner product (dot product) */
106 #define __fipr(x, y, z, w, a, b, c, d) ({ \
107  register float __x __asm__("fr0") = (x); \
108  register float __y __asm__("fr1") = (y); \
109  register float __z __asm__("fr2") = (z); \
110  register float __w __asm__("fr3") = (w); \
111  register float __a __asm__("fr4") = (a); \
112  register float __b __asm__("fr5") = (b); \
113  register float __c __asm__("fr6") = (c); \
114  register float __d __asm__("fr7") = (d); \
115  __asm__ __volatile__( \
116  "fipr fv4,fv0" \
117  : "+f" (__w) \
118  : "f" (__x), "f" (__y), "f" (__z), "f" (__w), \
119  "f" (__a), "f" (__b), "f" (__c), "f" (__d) \
120  ); \
121  __w; })
122 
123 /* Floating point inner product w/self (square of vector magnitude) */
124 #define __fipr_magnitude_sqr(x, y, z, w) ({ \
125  register float __x __asm__("fr4") = (x); \
126  register float __y __asm__("fr5") = (y); \
127  register float __z __asm__("fr6") = (z); \
128  register float __w __asm__("fr7") = (w); \
129  __asm__ __volatile__( \
130  "fipr fv4,fv4" \
131  : "+f" (__w) \
132  : "f" (__x), "f" (__y), "f" (__z), "f" (__w) \
133  ); \
134  __w; })
135 
136 /** \endcond */
137 
138 /** \return v1 dot v2 (inner product) */
139 extern inline float fipr(float x, float y, float z, float w,
140  float a, float b, float c, float d) {
141  return __fipr(x, y, z, w, a, b, c, d);
142 }
143 
144 /**
145  \brief Floating point inner product w/self (square of vector magnitude)
146  \return v1 dot v1 (square of magnitude)
147 */
148 extern inline float fipr_magnitude_sqr(float x, float y, float z, float w) {
149  return __fipr_magnitude_sqr(x, y, z, w);
150 }
151 
152 /**
153  \brief Floating point sine
154  \param r a floating point number between 0 and 2*PI
155  \return sin(r), where r is [0..2*PI]
156 */
157 extern inline float fsin(float r) {
158  return __fsin(r);
159 }
160 
161 /**
162  \brief Floating point cosine
163  \param r a floating point number between 0 and 2*PI
164  \return cos(r), where r is [0..2*PI]
165 */
166 extern inline float fcos(float r) {
167  return __fcos(r);
168 }
169 
170 /**
171  \brief Floating point tangent
172  \param r a floating point number between 0 and 2*PI
173  \return tan(r), where r is [0..2*PI]
174 */
175 extern inline float ftan(float r) {
176  return __ftan(r);
177 }
178 
179 /**
180  \brief Integer sine
181  \param d an integer between 0 and 65535
182  \return sin(d), where d is [0..65535]
183 */
184 extern inline float fisin(int d) {
185  return __fisin(d);
186 }
187 
188 /**
189  \brief Integer cosine
190  \param d an integer between 0 and 65535
191  \return cos(d), where d is [0..65535]
192 */
193 extern inline float ficos(int d) {
194  return __ficos(d);
195 }
196 
197 /**
198  \brief Integer tangent
199  \param d an integer between 0 and 65535
200  \return tan(d), where d is [0..65535]
201 */
202 extern inline float fitan(int d) {
203  return __fitan(d);
204 }
205 
206 /**
207  \brief Floating point square root
208  \return sqrt(f)
209 */
210 extern inline float fsqrt(float f) {
211  return __fsqrt(f);
212 }
213 
214 /**
215  \return 1.0f / sqrt(f)
216 */
217 extern inline float frsqrt(float f) {
218  return __frsqrt(f);
219 }
220 
221 __END_DECLS
222 
223 #endif /* __DC_FMATH_H */
224