• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 #include "rs_types.rsh"
2 
3 // Conversions
4 #define CVT_FUNC_2(typeout, typein)                             \
5 extern typeout##2 __attribute__((overloadable))             \
6         convert_##typeout##2(typein##2 v) {                     \
7     typeout##2 r = {(typeout)v.x, (typeout)v.y};                \
8     return r;                                                   \
9 }                                                               \
10 extern typeout##3 __attribute__((overloadable))             \
11         convert_##typeout##3(typein##3 v) {                     \
12     typeout##3 r = {(typeout)v.x, (typeout)v.y, (typeout)v.z};  \
13     return r;                                                   \
14 }                                                               \
15 extern typeout##4 __attribute__((overloadable))             \
16         convert_##typeout##4(typein##4 v) {                     \
17     typeout##4 r = {(typeout)v.x, (typeout)v.y, (typeout)v.z,   \
18                     (typeout)v.w};                              \
19     return r;                                                   \
20 }
21 
22 #define CVT_FUNC(type)  CVT_FUNC_2(type, uchar)     \
23                         CVT_FUNC_2(type, char)      \
24                         CVT_FUNC_2(type, ushort)    \
25                         CVT_FUNC_2(type, short)     \
26                         CVT_FUNC_2(type, uint)      \
27                         CVT_FUNC_2(type, int)       \
28                         CVT_FUNC_2(type, float)
29 
30 CVT_FUNC(char)
31 CVT_FUNC(uchar)
32 CVT_FUNC(short)
33 CVT_FUNC(ushort)
34 CVT_FUNC(int)
35 CVT_FUNC(uint)
36 CVT_FUNC(float)
37 
38 // Float ops, 6.11.2
39 
40 #define FN_FUNC_FN(fnc)                                         \
41 extern float2 __attribute__((overloadable)) fnc(float2 v) { \
42     float2 r;                                                   \
43     r.x = fnc(v.x);                                             \
44     r.y = fnc(v.y);                                             \
45     return r;                                                   \
46 }                                                               \
47 extern float3 __attribute__((overloadable)) fnc(float3 v) { \
48     float3 r;                                                   \
49     r.x = fnc(v.x);                                             \
50     r.y = fnc(v.y);                                             \
51     r.z = fnc(v.z);                                             \
52     return r;                                                   \
53 }                                                               \
54 extern float4 __attribute__((overloadable)) fnc(float4 v) { \
55     float4 r;                                                   \
56     r.x = fnc(v.x);                                             \
57     r.y = fnc(v.y);                                             \
58     r.z = fnc(v.z);                                             \
59     r.w = fnc(v.w);                                             \
60     return r;                                                   \
61 }
62 
63 #define IN_FUNC_FN(fnc)                                         \
64 extern int2 __attribute__((overloadable)) fnc(float2 v) {   \
65     int2 r;                                                     \
66     r.x = fnc(v.x);                                             \
67     r.y = fnc(v.y);                                             \
68     return r;                                                   \
69 }                                                               \
70 extern int3 __attribute__((overloadable)) fnc(float3 v) {   \
71     int3 r;                                                     \
72     r.x = fnc(v.x);                                             \
73     r.y = fnc(v.y);                                             \
74     r.z = fnc(v.z);                                             \
75     return r;                                                   \
76 }                                                               \
77 extern int4 __attribute__((overloadable)) fnc(float4 v) {   \
78     int4 r;                                                     \
79     r.x = fnc(v.x);                                             \
80     r.y = fnc(v.y);                                             \
81     r.z = fnc(v.z);                                             \
82     r.w = fnc(v.w);                                             \
83     return r;                                                   \
84 }
85 
86 #define FN_FUNC_FN_FN(fnc)                                                  \
87 extern float2 __attribute__((overloadable)) fnc(float2 v1, float2 v2) { \
88     float2 r;                                                               \
89     r.x = fnc(v1.x, v2.x);                                                  \
90     r.y = fnc(v1.y, v2.y);                                                  \
91     return r;                                                               \
92 }                                                                           \
93 extern float3 __attribute__((overloadable)) fnc(float3 v1, float3 v2) { \
94     float3 r;                                                               \
95     r.x = fnc(v1.x, v2.x);                                                  \
96     r.y = fnc(v1.y, v2.y);                                                  \
97     r.z = fnc(v1.z, v2.z);                                                  \
98     return r;                                                               \
99 }                                                                           \
100 extern float4 __attribute__((overloadable)) fnc(float4 v1, float4 v2) { \
101     float4 r;                                                               \
102     r.x = fnc(v1.x, v2.x);                                                  \
103     r.y = fnc(v1.y, v2.y);                                                  \
104     r.z = fnc(v1.z, v2.z);                                                  \
105     r.w = fnc(v1.w, v2.w);                                                  \
106     return r;                                                               \
107 }
108 
109 #define FN_FUNC_FN_F(fnc)                                                   \
110 extern float2 __attribute__((overloadable)) fnc(float2 v1, float v2) {  \
111     float2 r;                                                               \
112     r.x = fnc(v1.x, v2);                                                    \
113     r.y = fnc(v1.y, v2);                                                    \
114     return r;                                                               \
115 }                                                                           \
116 extern float3 __attribute__((overloadable)) fnc(float3 v1, float v2) {  \
117     float3 r;                                                               \
118     r.x = fnc(v1.x, v2);                                                    \
119     r.y = fnc(v1.y, v2);                                                    \
120     r.z = fnc(v1.z, v2);                                                    \
121     return r;                                                               \
122 }                                                                           \
123 extern float4 __attribute__((overloadable)) fnc(float4 v1, float v2) {  \
124     float4 r;                                                               \
125     r.x = fnc(v1.x, v2);                                                    \
126     r.y = fnc(v1.y, v2);                                                    \
127     r.z = fnc(v1.z, v2);                                                    \
128     r.w = fnc(v1.w, v2);                                                    \
129     return r;                                                               \
130 }
131 
132 #define FN_FUNC_FN_IN(fnc)                                                  \
133 extern float2 __attribute__((overloadable)) fnc(float2 v1, int2 v2) {   \
134     float2 r;                                                               \
135     r.x = fnc(v1.x, v2.x);                                                  \
136     r.y = fnc(v1.y, v2.y);                                                  \
137     return r;                                                               \
138 }                                                                           \
139 extern float3 __attribute__((overloadable)) fnc(float3 v1, int3 v2) {   \
140     float3 r;                                                               \
141     r.x = fnc(v1.x, v2.x);                                                  \
142     r.y = fnc(v1.y, v2.y);                                                  \
143     r.z = fnc(v1.z, v2.z);                                                  \
144     return r;                                                               \
145 }                                                                           \
146 extern float4 __attribute__((overloadable)) fnc(float4 v1, int4 v2) {   \
147     float4 r;                                                               \
148     r.x = fnc(v1.x, v2.x);                                                  \
149     r.y = fnc(v1.y, v2.y);                                                  \
150     r.z = fnc(v1.z, v2.z);                                                  \
151     r.w = fnc(v1.w, v2.w);                                                  \
152     return r;                                                               \
153 }
154 
155 #define FN_FUNC_FN_I(fnc)                                                   \
156 extern float2 __attribute__((overloadable)) fnc(float2 v1, int v2) {    \
157     float2 r;                                                               \
158     r.x = fnc(v1.x, v2);                                                    \
159     r.y = fnc(v1.y, v2);                                                    \
160     return r;                                                               \
161 }                                                                           \
162 extern float3 __attribute__((overloadable)) fnc(float3 v1, int v2) {    \
163     float3 r;                                                               \
164     r.x = fnc(v1.x, v2);                                                    \
165     r.y = fnc(v1.y, v2);                                                    \
166     r.z = fnc(v1.z, v2);                                                    \
167     return r;                                                               \
168 }                                                                           \
169 extern float4 __attribute__((overloadable)) fnc(float4 v1, int v2) {    \
170     float4 r;                                                               \
171     r.x = fnc(v1.x, v2);                                                    \
172     r.y = fnc(v1.y, v2);                                                    \
173     r.z = fnc(v1.z, v2);                                                    \
174     r.w = fnc(v1.w, v2);                                                    \
175     return r;                                                               \
176 }
177 
178 #define FN_FUNC_FN_PFN(fnc)                     \
179 extern float2 __attribute__((overloadable)) \
180         fnc(float2 v1, float2 *v2) {            \
181     float2 r;                                   \
182     float t[2];                                 \
183     r.x = fnc(v1.x, &t[0]);                     \
184     r.y = fnc(v1.y, &t[1]);                     \
185     v2->x = t[0];                               \
186     v2->y = t[1];                               \
187     return r;                                   \
188 }                                               \
189 extern float3 __attribute__((overloadable)) \
190         fnc(float3 v1, float3 *v2) {            \
191     float3 r;                                   \
192     float t[3];                                 \
193     r.x = fnc(v1.x, &t[0]);                     \
194     r.y = fnc(v1.y, &t[1]);                     \
195     r.z = fnc(v1.z, &t[2]);                     \
196     v2->x = t[0];                               \
197     v2->y = t[1];                               \
198     v2->z = t[2];                               \
199     return r;                                   \
200 }                                               \
201 extern float4 __attribute__((overloadable)) \
202         fnc(float4 v1, float4 *v2) {            \
203     float4 r;                                   \
204     float t[4];                                 \
205     r.x = fnc(v1.x, &t[0]);                     \
206     r.y = fnc(v1.y, &t[1]);                     \
207     r.z = fnc(v1.z, &t[2]);                     \
208     r.w = fnc(v1.w, &t[3]);                     \
209     v2->x = t[0];                               \
210     v2->y = t[1];                               \
211     v2->z = t[2];                               \
212     v2->w = t[3];                               \
213     return r;                                   \
214 }
215 
216 #define FN_FUNC_FN_PIN(fnc)                                                 \
217 extern float2 __attribute__((overloadable)) fnc(float2 v1, int2 *v2) {  \
218     float2 r;                                                               \
219     int t[2];                                                               \
220     r.x = fnc(v1.x, &t[0]);                                                 \
221     r.y = fnc(v1.y, &t[1]);                                                 \
222     v2->x = t[0];                                                           \
223     v2->y = t[1];                                                           \
224     return r;                                                               \
225 }                                                                           \
226 extern float3 __attribute__((overloadable)) fnc(float3 v1, int3 *v2) {  \
227     float3 r;                                                               \
228     int t[3];                                                               \
229     r.x = fnc(v1.x, &t[0]);                                                 \
230     r.y = fnc(v1.y, &t[1]);                                                 \
231     r.z = fnc(v1.z, &t[2]);                                                 \
232     v2->x = t[0];                                                           \
233     v2->y = t[1];                                                           \
234     v2->z = t[2];                                                           \
235     return r;                                                               \
236 }                                                                           \
237 extern float4 __attribute__((overloadable)) fnc(float4 v1, int4 *v2) {  \
238     float4 r;                                                               \
239     int t[4];                                                               \
240     r.x = fnc(v1.x, &t[0]);                                                 \
241     r.y = fnc(v1.y, &t[1]);                                                 \
242     r.z = fnc(v1.z, &t[2]);                                                 \
243     r.w = fnc(v1.w, &t[3]);                                                 \
244     v2->x = t[0];                                                           \
245     v2->y = t[1];                                                           \
246     v2->z = t[2];                                                           \
247     v2->w = t[3];                                                           \
248     return r;                                                               \
249 }
250 
251 #define FN_FUNC_FN_FN_FN(fnc)                   \
252 extern float2 __attribute__((overloadable)) \
253         fnc(float2 v1, float2 v2, float2 v3) {  \
254     float2 r;                                   \
255     r.x = fnc(v1.x, v2.x, v3.x);                \
256     r.y = fnc(v1.y, v2.y, v3.y);                \
257     return r;                                   \
258 }                                               \
259 extern float3 __attribute__((overloadable)) \
260         fnc(float3 v1, float3 v2, float3 v3) {  \
261     float3 r;                                   \
262     r.x = fnc(v1.x, v2.x, v3.x);                \
263     r.y = fnc(v1.y, v2.y, v3.y);                \
264     r.z = fnc(v1.z, v2.z, v3.z);                \
265     return r;                                   \
266 }                                               \
267 extern float4 __attribute__((overloadable)) \
268         fnc(float4 v1, float4 v2, float4 v3) {  \
269     float4 r;                                   \
270     r.x = fnc(v1.x, v2.x, v3.x);                \
271     r.y = fnc(v1.y, v2.y, v3.y);                \
272     r.z = fnc(v1.z, v2.z, v3.z);                \
273     r.w = fnc(v1.w, v2.w, v3.w);                \
274     return r;                                   \
275 }
276 
277 #define FN_FUNC_FN_FN_PIN(fnc)                  \
278 extern float2 __attribute__((overloadable)) \
279         fnc(float2 v1, float2 v2, int2 *v3) {   \
280     float2 r;                                   \
281     int t[2];                                   \
282     r.x = fnc(v1.x, v2.x, &t[0]);               \
283     r.y = fnc(v1.y, v2.y, &t[1]);               \
284     v3->x = t[0];                               \
285     v3->y = t[1];                               \
286     return r;                                   \
287 }                                               \
288 extern float3 __attribute__((overloadable)) \
289         fnc(float3 v1, float3 v2, int3 *v3) {   \
290     float3 r;                                   \
291     int t[3];                                   \
292     r.x = fnc(v1.x, v2.x, &t[0]);               \
293     r.y = fnc(v1.y, v2.y, &t[1]);               \
294     r.z = fnc(v1.z, v2.z, &t[2]);               \
295     v3->x = t[0];                               \
296     v3->y = t[1];                               \
297     v3->z = t[2];                               \
298     return r;                                   \
299 }                                               \
300 extern float4 __attribute__((overloadable)) \
301         fnc(float4 v1, float4 v2, int4 *v3) {   \
302     float4 r;                                   \
303     int t[4];                                   \
304     r.x = fnc(v1.x, v2.x, &t[0]);               \
305     r.y = fnc(v1.y, v2.y, &t[1]);               \
306     r.z = fnc(v1.z, v2.z, &t[2]);               \
307     r.w = fnc(v1.w, v2.w, &t[3]);               \
308     v3->x = t[0];                               \
309     v3->y = t[1];                               \
310     v3->z = t[2];                               \
311     v3->w = t[3];                               \
312     return r;                                   \
313 }
314 
315 extern float __attribute__((overloadable)) acos(float);
316 FN_FUNC_FN(acos)
317 
318 extern float __attribute__((overloadable)) acosh(float);
FN_FUNC_FN(acosh)319 FN_FUNC_FN(acosh)
320 
321 
322 extern float __attribute__((overloadable)) acospi(float v) {
323     return acos(v) / M_PI;
324 }
325 FN_FUNC_FN(acospi)
326 
327 extern float __attribute__((overloadable)) asin(float);
328 FN_FUNC_FN(asin)
329 
330 extern float __attribute__((overloadable)) asinh(float);
FN_FUNC_FN(asinh)331 FN_FUNC_FN(asinh)
332 
333 extern float __attribute__((overloadable)) asinpi(float v) {
334     return asin(v) / M_PI;
335 }
336 FN_FUNC_FN(asinpi)
337 
338 extern float __attribute__((overloadable)) atan(float);
339 FN_FUNC_FN(atan)
340 
341 extern float __attribute__((overloadable)) atan2(float, float);
342 FN_FUNC_FN_FN(atan2)
343 
344 extern float __attribute__((overloadable)) atanh(float);
FN_FUNC_FN(atanh)345 FN_FUNC_FN(atanh)
346 
347 extern float __attribute__((overloadable)) atanpi(float v) {
348     return atan(v) / M_PI;
349 }
FN_FUNC_FN(atanpi)350 FN_FUNC_FN(atanpi)
351 
352 
353 extern float __attribute__((overloadable)) atan2pi(float y, float x) {
354     return atan2(y, x) / M_PI;
355 }
356 FN_FUNC_FN_FN(atan2pi)
357 
358 extern float __attribute__((overloadable)) cbrt(float);
359 FN_FUNC_FN(cbrt)
360 
361 extern float __attribute__((overloadable)) ceil(float);
362 FN_FUNC_FN(ceil)
363 
364 extern float __attribute__((overloadable)) copysign(float, float);
365 FN_FUNC_FN_FN(copysign)
366 
367 extern float __attribute__((overloadable)) cos(float);
368 FN_FUNC_FN(cos)
369 
370 extern float __attribute__((overloadable)) cosh(float);
FN_FUNC_FN(cosh)371 FN_FUNC_FN(cosh)
372 
373 extern float __attribute__((overloadable)) cospi(float v) {
374     return cos(v * M_PI);
375 }
376 FN_FUNC_FN(cospi)
377 
378 extern float __attribute__((overloadable)) erfc(float);
379 FN_FUNC_FN(erfc)
380 
381 extern float __attribute__((overloadable)) erf(float);
382 FN_FUNC_FN(erf)
383 
384 extern float __attribute__((overloadable)) exp(float);
385 FN_FUNC_FN(exp)
386 
387 extern float __attribute__((overloadable)) exp2(float);
388 FN_FUNC_FN(exp2)
389 
390 extern float __attribute__((overloadable)) pow(float, float);
391 
exp10(float v)392 extern float __attribute__((overloadable)) exp10(float v) {
393     return pow(10.f, v);
394 }
395 FN_FUNC_FN(exp10)
396 
397 extern float __attribute__((overloadable)) expm1(float);
398 FN_FUNC_FN(expm1)
399 
400 extern float __attribute__((overloadable)) fabs(float);
401 FN_FUNC_FN(fabs)
402 
403 extern float __attribute__((overloadable)) fdim(float, float);
404 FN_FUNC_FN_FN(fdim)
405 
406 extern float __attribute__((overloadable)) floor(float);
407 FN_FUNC_FN(floor)
408 
409 extern float __attribute__((overloadable)) fma(float, float, float);
410 FN_FUNC_FN_FN_FN(fma)
411 
412 extern float __attribute__((overloadable)) fmax(float, float);
413 FN_FUNC_FN_FN(fmax);
414 FN_FUNC_FN_F(fmax);
415 
416 extern float __attribute__((overloadable)) fmin(float, float);
417 FN_FUNC_FN_FN(fmin);
418 FN_FUNC_FN_F(fmin);
419 
420 extern float __attribute__((overloadable)) fmod(float, float);
FN_FUNC_FN_FN(fmod)421 FN_FUNC_FN_FN(fmod)
422 
423 extern float __attribute__((overloadable)) fract(float v, float *iptr) {
424     int i = (int)floor(v);
425     iptr[0] = i;
426     return fmin(v - i, 0x1.fffffep-1f);
427 }
428 FN_FUNC_FN_PFN(fract)
429 
430 extern float __attribute__((overloadable)) frexp(float, int *);
431 FN_FUNC_FN_PIN(frexp)
432 
433 extern float __attribute__((overloadable)) hypot(float, float);
434 FN_FUNC_FN_FN(hypot)
435 
436 extern int __attribute__((overloadable)) ilogb(float);
437 IN_FUNC_FN(ilogb)
438 
439 extern float __attribute__((overloadable)) ldexp(float, int);
440 FN_FUNC_FN_IN(ldexp)
441 FN_FUNC_FN_I(ldexp)
442 
443 extern float __attribute__((overloadable)) lgamma(float);
444 FN_FUNC_FN(lgamma)
445 extern float __attribute__((overloadable)) lgamma(float, int*);
446 FN_FUNC_FN_PIN(lgamma)
447 
448 extern float __attribute__((overloadable)) log(float);
449 FN_FUNC_FN(log)
450 
451 extern float __attribute__((overloadable)) log10(float);
FN_FUNC_FN(log10)452 FN_FUNC_FN(log10)
453 
454 
455 extern float __attribute__((overloadable)) log2(float v) {
456     return log10(v) / log10(2.f);
457 }
458 FN_FUNC_FN(log2)
459 
460 extern float __attribute__((overloadable)) log1p(float);
461 FN_FUNC_FN(log1p)
462 
463 extern float __attribute__((overloadable)) logb(float);
464 FN_FUNC_FN(logb)
465 
466 extern float __attribute__((overloadable)) mad(float, float, float);
467 FN_FUNC_FN_FN_FN(mad)
468 
469 extern float __attribute__((overloadable)) modf(float, float *);
470 FN_FUNC_FN_PFN(modf);
471 
472 //extern float __attribute__((overloadable)) nan(uint);
473 
474 extern float __attribute__((overloadable)) nextafter(float, float);
475 FN_FUNC_FN_FN(nextafter)
476 
FN_FUNC_FN_FN(pow)477 FN_FUNC_FN_FN(pow)
478 
479 extern float __attribute__((overloadable)) pown(float v, int p) {
480     return pow(v, (float)p);
481 }
pown(float2 v,int2 p)482 extern float2 __attribute__((overloadable)) pown(float2 v, int2 p) {
483     return pow(v, (float2)p);
484 }
pown(float3 v,int3 p)485 extern float3 __attribute__((overloadable)) pown(float3 v, int3 p) {
486     return pow(v, (float3)p);
487 }
pown(float4 v,int4 p)488 extern float4 __attribute__((overloadable)) pown(float4 v, int4 p) {
489     return pow(v, (float4)p);
490 }
491 
powr(float v,float p)492 extern float __attribute__((overloadable)) powr(float v, float p) {
493     return pow(v, p);
494 }
powr(float2 v,float2 p)495 extern float2 __attribute__((overloadable)) powr(float2 v, float2 p) {
496     return pow(v, p);
497 }
powr(float3 v,float3 p)498 extern float3 __attribute__((overloadable)) powr(float3 v, float3 p) {
499     return pow(v, p);
500 }
powr(float4 v,float4 p)501 extern float4 __attribute__((overloadable)) powr(float4 v, float4 p) {
502     return pow(v, p);
503 }
504 
505 extern float __attribute__((overloadable)) remainder(float, float);
506 FN_FUNC_FN_FN(remainder)
507 
508 extern float __attribute__((overloadable)) remquo(float, float, int *);
509 FN_FUNC_FN_FN_PIN(remquo)
510 
511 extern float __attribute__((overloadable)) rint(float);
FN_FUNC_FN(rint)512 FN_FUNC_FN(rint)
513 
514 extern float __attribute__((overloadable)) rootn(float v, int r) {
515     return pow(v, 1.f / r);
516 }
rootn(float2 v,int2 r)517 extern float2 __attribute__((overloadable)) rootn(float2 v, int2 r) {
518     float2 t = {1.f / r.x, 1.f / r.y};
519     return pow(v, t);
520 }
rootn(float3 v,int3 r)521 extern float3 __attribute__((overloadable)) rootn(float3 v, int3 r) {
522     float3 t = {1.f / r.x, 1.f / r.y, 1.f / r.z};
523     return pow(v, t);
524 }
rootn(float4 v,int4 r)525 extern float4 __attribute__((overloadable)) rootn(float4 v, int4 r) {
526     float4 t = {1.f / r.x, 1.f / r.y, 1.f / r.z, 1.f / r.w};
527     return pow(v, t);
528 }
529 
530 extern float __attribute__((overloadable)) round(float);
531 FN_FUNC_FN(round)
532 
533 
534 extern float __attribute__((overloadable)) sqrt(float);
rsqrt(float v)535 extern float __attribute__((overloadable)) rsqrt(float v) {
536     return 1.f / sqrt(v);
537 }
538 FN_FUNC_FN(rsqrt)
539 
540 extern float __attribute__((overloadable)) sin(float);
FN_FUNC_FN(sin)541 FN_FUNC_FN(sin)
542 
543 extern float __attribute__((overloadable)) sincos(float v, float *cosptr) {
544     *cosptr = cos(v);
545     return sin(v);
546 }
sincos(float2 v,float2 * cosptr)547 extern float2 __attribute__((overloadable)) sincos(float2 v, float2 *cosptr) {
548     *cosptr = cos(v);
549     return sin(v);
550 }
sincos(float3 v,float3 * cosptr)551 extern float3 __attribute__((overloadable)) sincos(float3 v, float3 *cosptr) {
552     *cosptr = cos(v);
553     return sin(v);
554 }
sincos(float4 v,float4 * cosptr)555 extern float4 __attribute__((overloadable)) sincos(float4 v, float4 *cosptr) {
556     *cosptr = cos(v);
557     return sin(v);
558 }
559 
560 extern float __attribute__((overloadable)) sinh(float);
FN_FUNC_FN(sinh)561 FN_FUNC_FN(sinh)
562 
563 extern float __attribute__((overloadable)) sinpi(float v) {
564     return sin(v * M_PI);
565 }
566 FN_FUNC_FN(sinpi)
567 
568 FN_FUNC_FN(sqrt)
569 
570 extern float __attribute__((overloadable)) tan(float);
571 FN_FUNC_FN(tan)
572 
573 extern float __attribute__((overloadable)) tanh(float);
FN_FUNC_FN(tanh)574 FN_FUNC_FN(tanh)
575 
576 extern float __attribute__((overloadable)) tanpi(float v) {
577     return tan(v * M_PI);
578 }
579 FN_FUNC_FN(tanpi)
580 
581 
582 extern float __attribute__((overloadable)) tgamma(float);
583 FN_FUNC_FN(tgamma)
584 
585 extern float __attribute__((overloadable)) trunc(float);
586 FN_FUNC_FN(trunc)
587 
588 // Int ops (partial), 6.11.3
589 
590 #define XN_FUNC_YN(typeout, fnc, typein)                                \
591 extern typeout __attribute__((overloadable)) fnc(typein);               \
592 extern typeout##2 __attribute__((overloadable)) fnc(typein##2 v) {  \
593     typeout##2 r;                                                       \
594     r.x = fnc(v.x);                                                     \
595     r.y = fnc(v.y);                                                     \
596     return r;                                                           \
597 }                                                                       \
598 extern typeout##3 __attribute__((overloadable)) fnc(typein##3 v) {  \
599     typeout##3 r;                                                       \
600     r.x = fnc(v.x);                                                     \
601     r.y = fnc(v.y);                                                     \
602     r.z = fnc(v.z);                                                     \
603     return r;                                                           \
604 }                                                                       \
605 extern typeout##4 __attribute__((overloadable)) fnc(typein##4 v) {  \
606     typeout##4 r;                                                       \
607     r.x = fnc(v.x);                                                     \
608     r.y = fnc(v.y);                                                     \
609     r.z = fnc(v.z);                                                     \
610     r.w = fnc(v.w);                                                     \
611     return r;                                                           \
612 }
613 
614 
615 #define UIN_FUNC_IN(fnc)          \
616 XN_FUNC_YN(uchar, fnc, char)      \
617 XN_FUNC_YN(ushort, fnc, short)    \
618 XN_FUNC_YN(uint, fnc, int)
619 
620 #define IN_FUNC_IN(fnc)           \
621 XN_FUNC_YN(uchar, fnc, uchar)     \
622 XN_FUNC_YN(char, fnc, char)       \
623 XN_FUNC_YN(ushort, fnc, ushort)   \
624 XN_FUNC_YN(short, fnc, short)     \
625 XN_FUNC_YN(uint, fnc, uint)       \
626 XN_FUNC_YN(int, fnc, int)
627 
628 
629 #define XN_FUNC_XN_XN_BODY(type, fnc, body)         \
630 extern type __attribute__((overloadable))       \
631         fnc(type v1, type v2) {                     \
632     return body;                                    \
633 }                                                   \
634 extern type##2 __attribute__((overloadable))    \
635         fnc(type##2 v1, type##2 v2) {               \
636     type##2 r;                                      \
637     r.x = fnc(v1.x, v2.x);                          \
638     r.y = fnc(v1.y, v2.y);                          \
639     return r;                                       \
640 }                                                   \
641 extern type##3 __attribute__((overloadable))    \
642         fnc(type##3 v1, type##3 v2) {               \
643     type##3 r;                                      \
644     r.x = fnc(v1.x, v2.x);                          \
645     r.y = fnc(v1.y, v2.y);                          \
646     r.z = fnc(v1.z, v2.z);                          \
647     return r;                                       \
648 }                                                   \
649 extern type##4 __attribute__((overloadable))    \
650         fnc(type##4 v1, type##4 v2) {               \
651     type##4 r;                                      \
652     r.x = fnc(v1.x, v2.x);                          \
653     r.y = fnc(v1.y, v2.y);                          \
654     r.z = fnc(v1.z, v2.z);                          \
655     r.w = fnc(v1.w, v2.w);                          \
656     return r;                                       \
657 }
658 
659 #define IN_FUNC_IN_IN_BODY(fnc, body) \
660 XN_FUNC_XN_XN_BODY(uchar, fnc, body)  \
661 XN_FUNC_XN_XN_BODY(char, fnc, body)   \
662 XN_FUNC_XN_XN_BODY(ushort, fnc, body) \
663 XN_FUNC_XN_XN_BODY(short, fnc, body)  \
664 XN_FUNC_XN_XN_BODY(uint, fnc, body)   \
665 XN_FUNC_XN_XN_BODY(int, fnc, body)    \
666 XN_FUNC_XN_XN_BODY(float, fnc, body)
667 
UIN_FUNC_IN(abs)668 UIN_FUNC_IN(abs)
669 IN_FUNC_IN(clz)
670 
671 IN_FUNC_IN_IN_BODY(min, (v1 < v2 ? v1 : v2))
672 FN_FUNC_FN_F(min)
673 
674 IN_FUNC_IN_IN_BODY(max, (v1 > v2 ? v1 : v2))
675 FN_FUNC_FN_F(max)
676 
677 
678 // 6.11.4
679 
680 extern float __attribute__((overloadable)) clamp(float amount, float low, float high) {
681     return amount < low ? low : (amount > high ? high : amount);
682 }
clamp(float2 amount,float2 low,float2 high)683 extern float2 __attribute__((overloadable)) clamp(float2 amount, float2 low, float2 high) {
684     float2 r;
685     r.x = amount.x < low.x ? low.x : (amount.x > high.x ? high.x : amount.x);
686     r.y = amount.y < low.y ? low.y : (amount.y > high.y ? high.y : amount.y);
687     return r;
688 }
clamp(float3 amount,float3 low,float3 high)689 extern float3 __attribute__((overloadable)) clamp(float3 amount, float3 low, float3 high) {
690     float3 r;
691     r.x = amount.x < low.x ? low.x : (amount.x > high.x ? high.x : amount.x);
692     r.y = amount.y < low.y ? low.y : (amount.y > high.y ? high.y : amount.y);
693     r.z = amount.z < low.z ? low.z : (amount.z > high.z ? high.z : amount.z);
694     return r;
695 }
clamp(float4 amount,float4 low,float4 high)696 extern float4 __attribute__((overloadable)) clamp(float4 amount, float4 low, float4 high) {
697     float4 r;
698     r.x = amount.x < low.x ? low.x : (amount.x > high.x ? high.x : amount.x);
699     r.y = amount.y < low.y ? low.y : (amount.y > high.y ? high.y : amount.y);
700     r.z = amount.z < low.z ? low.z : (amount.z > high.z ? high.z : amount.z);
701     r.w = amount.w < low.w ? low.w : (amount.w > high.w ? high.w : amount.w);
702     return r;
703 }
clamp(float2 amount,float low,float high)704 extern float2 __attribute__((overloadable)) clamp(float2 amount, float low, float high) {
705     float2 r;
706     r.x = amount.x < low ? low : (amount.x > high ? high : amount.x);
707     r.y = amount.y < low ? low : (amount.y > high ? high : amount.y);
708     return r;
709 }
clamp(float3 amount,float low,float high)710 extern float3 __attribute__((overloadable)) clamp(float3 amount, float low, float high) {
711     float3 r;
712     r.x = amount.x < low ? low : (amount.x > high ? high : amount.x);
713     r.y = amount.y < low ? low : (amount.y > high ? high : amount.y);
714     r.z = amount.z < low ? low : (amount.z > high ? high : amount.z);
715     return r;
716 }
clamp(float4 amount,float low,float high)717 extern float4 __attribute__((overloadable)) clamp(float4 amount, float low, float high) {
718     float4 r;
719     r.x = amount.x < low ? low : (amount.x > high ? high : amount.x);
720     r.y = amount.y < low ? low : (amount.y > high ? high : amount.y);
721     r.z = amount.z < low ? low : (amount.z > high ? high : amount.z);
722     r.w = amount.w < low ? low : (amount.w > high ? high : amount.w);
723     return r;
724 }
725 
degrees(float radians)726 extern float __attribute__((overloadable)) degrees(float radians) {
727     return radians * (180.f / M_PI);
728 }
FN_FUNC_FN(degrees)729 FN_FUNC_FN(degrees)
730 
731 extern float __attribute__((overloadable)) mix(float start, float stop, float amount) {
732     return start + (stop - start) * amount;
733 }
mix(float2 start,float2 stop,float2 amount)734 extern float2 __attribute__((overloadable)) mix(float2 start, float2 stop, float2 amount) {
735     return start + (stop - start) * amount;
736 }
mix(float3 start,float3 stop,float3 amount)737 extern float3 __attribute__((overloadable)) mix(float3 start, float3 stop, float3 amount) {
738     return start + (stop - start) * amount;
739 }
mix(float4 start,float4 stop,float4 amount)740 extern float4 __attribute__((overloadable)) mix(float4 start, float4 stop, float4 amount) {
741     return start + (stop - start) * amount;
742 }
mix(float2 start,float2 stop,float amount)743 extern float2 __attribute__((overloadable)) mix(float2 start, float2 stop, float amount) {
744     return start + (stop - start) * amount;
745 }
mix(float3 start,float3 stop,float amount)746 extern float3 __attribute__((overloadable)) mix(float3 start, float3 stop, float amount) {
747     return start + (stop - start) * amount;
748 }
mix(float4 start,float4 stop,float amount)749 extern float4 __attribute__((overloadable)) mix(float4 start, float4 stop, float amount) {
750     return start + (stop - start) * amount;
751 }
752 
radians(float degrees)753 extern float __attribute__((overloadable)) radians(float degrees) {
754     return degrees * (M_PI / 180.f);
755 }
FN_FUNC_FN(radians)756 FN_FUNC_FN(radians)
757 
758 extern float __attribute__((overloadable)) step(float edge, float v) {
759     return (v < edge) ? 0.f : 1.f;
760 }
step(float2 edge,float2 v)761 extern float2 __attribute__((overloadable)) step(float2 edge, float2 v) {
762     float2 r;
763     r.x = (v.x < edge.x) ? 0.f : 1.f;
764     r.y = (v.y < edge.y) ? 0.f : 1.f;
765     return r;
766 }
step(float3 edge,float3 v)767 extern float3 __attribute__((overloadable)) step(float3 edge, float3 v) {
768     float3 r;
769     r.x = (v.x < edge.x) ? 0.f : 1.f;
770     r.y = (v.y < edge.y) ? 0.f : 1.f;
771     r.z = (v.z < edge.z) ? 0.f : 1.f;
772     return r;
773 }
step(float4 edge,float4 v)774 extern float4 __attribute__((overloadable)) step(float4 edge, float4 v) {
775     float4 r;
776     r.x = (v.x < edge.x) ? 0.f : 1.f;
777     r.y = (v.y < edge.y) ? 0.f : 1.f;
778     r.z = (v.z < edge.z) ? 0.f : 1.f;
779     r.w = (v.w < edge.w) ? 0.f : 1.f;
780     return r;
781 }
step(float2 edge,float v)782 extern float2 __attribute__((overloadable)) step(float2 edge, float v) {
783     float2 r;
784     r.x = (v < edge.x) ? 0.f : 1.f;
785     r.y = (v < edge.y) ? 0.f : 1.f;
786     return r;
787 }
step(float3 edge,float v)788 extern float3 __attribute__((overloadable)) step(float3 edge, float v) {
789     float3 r;
790     r.x = (v < edge.x) ? 0.f : 1.f;
791     r.y = (v < edge.y) ? 0.f : 1.f;
792     r.z = (v < edge.z) ? 0.f : 1.f;
793     return r;
794 }
step(float4 edge,float v)795 extern float4 __attribute__((overloadable)) step(float4 edge, float v) {
796     float4 r;
797     r.x = (v < edge.x) ? 0.f : 1.f;
798     r.y = (v < edge.y) ? 0.f : 1.f;
799     r.z = (v < edge.z) ? 0.f : 1.f;
800     r.w = (v < edge.w) ? 0.f : 1.f;
801     return r;
802 }
803 
804 extern float __attribute__((overloadable)) smoothstep(float, float, float);
805 extern float2 __attribute__((overloadable)) smoothstep(float2, float2, float2);
806 extern float3 __attribute__((overloadable)) smoothstep(float3, float3, float3);
807 extern float4 __attribute__((overloadable)) smoothstep(float4, float4, float4);
808 extern float2 __attribute__((overloadable)) smoothstep(float, float, float2);
809 extern float3 __attribute__((overloadable)) smoothstep(float, float, float3);
810 extern float4 __attribute__((overloadable)) smoothstep(float, float, float4);
811 
sign(float v)812 extern float __attribute__((overloadable)) sign(float v) {
813     if (v > 0) return 1.f;
814     if (v < 0) return -1.f;
815     return v;
816 }
FN_FUNC_FN(sign)817 FN_FUNC_FN(sign)
818 
819 
820 // 6.11.5
821 extern float3 __attribute__((overloadable)) cross(float3 lhs, float3 rhs) {
822     float3 r;
823     r.x = lhs.y * rhs.z  - lhs.z * rhs.y;
824     r.y = lhs.z * rhs.x  - lhs.x * rhs.z;
825     r.z = lhs.x * rhs.y  - lhs.y * rhs.x;
826     return r;
827 }
828 
cross(float4 lhs,float4 rhs)829 extern float4 __attribute__((overloadable)) cross(float4 lhs, float4 rhs) {
830     float4 r;
831     r.x = lhs.y * rhs.z  - lhs.z * rhs.y;
832     r.y = lhs.z * rhs.x  - lhs.x * rhs.z;
833     r.z = lhs.x * rhs.y  - lhs.y * rhs.x;
834     r.w = 0.f;
835     return r;
836 }
837 
dot(float lhs,float rhs)838 extern float __attribute__((overloadable)) dot(float lhs, float rhs) {
839     return lhs * rhs;
840 }
dot(float2 lhs,float2 rhs)841 extern float __attribute__((overloadable)) dot(float2 lhs, float2 rhs) {
842     return lhs.x*rhs.x + lhs.y*rhs.y;
843 }
dot(float3 lhs,float3 rhs)844 extern float __attribute__((overloadable)) dot(float3 lhs, float3 rhs) {
845     return lhs.x*rhs.x + lhs.y*rhs.y + lhs.z*rhs.z;
846 }
dot(float4 lhs,float4 rhs)847 extern float __attribute__((overloadable)) dot(float4 lhs, float4 rhs) {
848     return lhs.x*rhs.x + lhs.y*rhs.y + lhs.z*rhs.z + lhs.w*rhs.w;
849 }
850 
length(float v)851 extern float __attribute__((overloadable)) length(float v) {
852     return v;
853 }
length(float2 v)854 extern float __attribute__((overloadable)) length(float2 v) {
855     return sqrt(v.x*v.x + v.y*v.y);
856 }
length(float3 v)857 extern float __attribute__((overloadable)) length(float3 v) {
858     return sqrt(v.x*v.x + v.y*v.y + v.z*v.z);
859 }
length(float4 v)860 extern float __attribute__((overloadable)) length(float4 v) {
861     return sqrt(v.x*v.x + v.y*v.y + v.z*v.z + v.w*v.w);
862 }
863 
distance(float lhs,float rhs)864 extern float __attribute__((overloadable)) distance(float lhs, float rhs) {
865     return length(lhs - rhs);
866 }
distance(float2 lhs,float2 rhs)867 extern float __attribute__((overloadable)) distance(float2 lhs, float2 rhs) {
868     return length(lhs - rhs);
869 }
distance(float3 lhs,float3 rhs)870 extern float __attribute__((overloadable)) distance(float3 lhs, float3 rhs) {
871     return length(lhs - rhs);
872 }
distance(float4 lhs,float4 rhs)873 extern float __attribute__((overloadable)) distance(float4 lhs, float4 rhs) {
874     return length(lhs - rhs);
875 }
876 
normalize(float v)877 extern float __attribute__((overloadable)) normalize(float v) {
878     return 1.f;
879 }
normalize(float2 v)880 extern float2 __attribute__((overloadable)) normalize(float2 v) {
881     return v / length(v);
882 }
normalize(float3 v)883 extern float3 __attribute__((overloadable)) normalize(float3 v) {
884     return v / length(v);
885 }
normalize(float4 v)886 extern float4 __attribute__((overloadable)) normalize(float4 v) {
887     return v / length(v);
888 }
889 
890 #undef CVT_FUNC
891 #undef CVT_FUNC_2
892 #undef FN_FUNC_FN
893 #undef IN_FUNC_FN
894 #undef FN_FUNC_FN_FN
895 #undef FN_FUNC_FN_F
896 #undef FN_FUNC_FN_IN
897 #undef FN_FUNC_FN_I
898 #undef FN_FUNC_FN_PFN
899 #undef FN_FUNC_FN_PIN
900 #undef FN_FUNC_FN_FN_FN
901 #undef FN_FUNC_FN_FN_PIN
902 #undef XN_FUNC_YN
903 #undef UIN_FUNC_IN
904 #undef IN_FUNC_IN
905 #undef XN_FUNC_XN_XN_BODY
906 #undef IN_FUNC_IN_IN_BODY
907