1 #if defined(__CUDA_ARCH__)
2 #include "chrono/multicore_math/simd_non.h"
3 #include "chrono/multicore_math/real3.h"
4 #include <iostream>
5 
6 namespace chrono {
7 
Set3(real x)8 CUDA_HOST_DEVICE real3 Set3(real x) {
9     return real3(x);
10 }
Set3(real x,real y,real z)11 CUDA_HOST_DEVICE real3 Set3(real x, real y, real z) {
12     return real3(x, y, z);
13 }
14 
15 //========================================================
operator +(const real3 & a,const real3 & b)16 CUDA_HOST_DEVICE real3 operator+(const real3& a, const real3& b) {
17     return simd::Add(a, b);
18 }
operator -(const real3 & a,const real3 & b)19 CUDA_HOST_DEVICE real3 operator-(const real3& a, const real3& b) {
20     return simd::Sub(a, b);
21 }
operator *(const real3 & a,const real3 & b)22 CUDA_HOST_DEVICE real3 operator*(const real3& a, const real3& b) {
23     return simd::Mul(a, b);
24 }
operator /(const real3 & a,const real3 & b)25 CUDA_HOST_DEVICE real3 operator/(const real3& a, const real3& b) {
26     return simd::Div(a, b);
27 }
28 //========================================================
operator +(const real3 & a,real b)29 CUDA_HOST_DEVICE real3 operator+(const real3& a, real b) {
30     return simd::Add(a, Set3(b));
31 }
operator -(const real3 & a,real b)32 CUDA_HOST_DEVICE real3 operator-(const real3& a, real b) {
33     return simd::Sub(a, Set3(b));
34 }
operator *(const real3 & a,real b)35 CUDA_HOST_DEVICE real3 operator*(const real3& a, real b) {
36     return simd::Mul(a, Set3(b));
37 }
operator /(const real3 & a,real b)38 CUDA_HOST_DEVICE real3 operator/(const real3& a, real b) {
39     return simd::Div(a, Set3(b));
40 }
operator *(real lhs,const real3 & rhs)41 CUDA_HOST_DEVICE real3 operator*(real lhs, const real3& rhs) {
42     return simd::Mul(Set3(lhs), rhs);
43 }
operator /(real lhs,const real3 & rhs)44 CUDA_HOST_DEVICE real3 operator/(real lhs, const real3& rhs) {
45     return simd::Div(Set3(lhs), rhs);
46 }
operator -(const real3 & a)47 CUDA_HOST_DEVICE real3 operator-(const real3& a) {
48     return simd::Negate(a);
49 }
50 //========================================================
51 
52 CUDA_HOST_DEVICE OPERATOR_EQUALS_IMPL(*, real, real3);
53 CUDA_HOST_DEVICE OPERATOR_EQUALS_IMPL(/, real, real3);
54 CUDA_HOST_DEVICE OPERATOR_EQUALS_IMPL(+, real, real3);
55 CUDA_HOST_DEVICE OPERATOR_EQUALS_IMPL(-, real, real3);
56 
57 CUDA_HOST_DEVICE OPERATOR_EQUALS_IMPL(*, real3, real3);
58 CUDA_HOST_DEVICE OPERATOR_EQUALS_IMPL(/, real3, real3);
59 CUDA_HOST_DEVICE OPERATOR_EQUALS_IMPL(+, real3, real3);
60 CUDA_HOST_DEVICE OPERATOR_EQUALS_IMPL(-, real3, real3);
61 
Dot(const real3 & v1,const real3 & v2)62 CUDA_HOST_DEVICE real Dot(const real3& v1, const real3& v2) {
63     return v1.x * v2.x + v1.y * v2.y + v1.z * v2.z;
64     // return simd::Dot3(v1, v2);
65 }
Dot(const real3 & v)66 CUDA_HOST_DEVICE real Dot(const real3& v) {
67     return v.x * v.x + v.y * v.y + v.z * v.z;
68     // return simd::Dot3(v);
69 }
70 
Normalize(const real3 & v)71 CUDA_HOST_DEVICE real3 Normalize(const real3& v) {
72     // return simd::Normalize3(v);
73     return v / Sqrt(Dot(v));
74 }
Length(const real3 & v)75 CUDA_HOST_DEVICE real Length(const real3& v) {
76     return Sqrt(Dot(v));
77     // return simd::Length3(v);
78 }
Sqrt(const real3 & v)79 CUDA_HOST_DEVICE real3 Sqrt(const real3& v) {
80     return simd::SquareRoot(v);
81 }
Cross(const real3 & b,const real3 & c)82 CUDA_HOST_DEVICE real3 Cross(const real3& b, const real3& c) {
83     return simd::Cross3(b, c);
84 }
Abs(const real3 & v)85 CUDA_HOST_DEVICE real3 Abs(const real3& v) {
86     return simd::Abs(v);
87 }
Sign(const real3 & v)88 CUDA_HOST_DEVICE real3 Sign(const real3& v) {
89     return simd::Max(simd::Min(v, Set3(1)), Set3(-1));
90 }
Max(const real3 & a,const real3 & b)91 CUDA_HOST_DEVICE real3 Max(const real3& a, const real3& b) {
92     return simd::Max(a, b);
93 }
94 
Min(const real3 & a,const real3 & b)95 CUDA_HOST_DEVICE real3 Min(const real3& a, const real3& b) {
96     return simd::Min(a, b);
97 }
98 
Max(const real3 & a,const real & b)99 CUDA_HOST_DEVICE real3 Max(const real3& a, const real& b) {
100     return simd::Max(a, Set3(b));
101 }
102 
Min(const real3 & a,const real & b)103 CUDA_HOST_DEVICE real3 Min(const real3& a, const real& b) {
104     return simd::Min(a, Set3(b));
105 }
Max(const real3 & a)106 CUDA_HOST_DEVICE real Max(const real3& a) {
107     return simd::Max(a);
108 }
Min(const real3 & a)109 CUDA_HOST_DEVICE real Min(const real3& a) {
110     return simd::Min(a);
111 }
112 
Length2(const real3 & v1)113 CUDA_HOST_DEVICE real Length2(const real3& v1) {
114     return Dot(v1);
115 }
116 
SafeLength(const real3 & v)117 CUDA_HOST_DEVICE real SafeLength(const real3& v) {
118     real len_sq = Length2(v);
119     if (len_sq) {
120         return Sqrt(len_sq);
121     } else {
122         return 0.0f;
123     }
124 }
125 
SafeNormalize(const real3 & v,const real3 & safe)126 CUDA_HOST_DEVICE real3 SafeNormalize(const real3& v, const real3& safe) {
127     real len_sq = Length2(v);
128     if (len_sq > real(0)) {
129         return v * InvSqrt(len_sq);
130     } else {
131         return safe;
132     }
133 }
134 
Clamp(const real3 & a,const real3 & clamp_min,const real3 & clamp_max)135 CUDA_HOST_DEVICE real3 Clamp(const real3& a, const real3& clamp_min, const real3& clamp_max) {
136     return simd::Max(clamp_min, simd::Min(a, clamp_max));
137 }
138 
Clamp(const real3 & v,real max_length)139 CUDA_HOST_DEVICE real3 Clamp(const real3& v, real max_length) {
140     real3 x = v;
141     real len_sq = Dot(x);
142     real inv_len = InvSqrt(len_sq);
143 
144     if (len_sq > Sqr(max_length))
145         x *= inv_len * max_length;
146 
147     return x;
148 }
149 
operator <(const real3 & a,const real3 & b)150 CUDA_HOST_DEVICE bool operator<(const real3& a, const real3& b) {
151     if (a.x < b.x) {
152         return true;
153     }
154     if (b.x < a.x) {
155         return false;
156     }
157     if (a.y < b.y) {
158         return true;
159     }
160     if (b.y < a.y) {
161         return false;
162     }
163     if (a.z < b.z) {
164         return true;
165     }
166     if (b.z < a.z) {
167         return false;
168     }
169     return false;
170 }
operator >(const real3 & a,const real3 & b)171 CUDA_HOST_DEVICE bool operator>(const real3& a, const real3& b) {
172     if (a.x > b.x) {
173         return true;
174     }
175     if (b.x > a.x) {
176         return false;
177     }
178     if (a.y > b.y) {
179         return true;
180     }
181     if (b.y > a.y) {
182         return false;
183     }
184     if (a.z > b.z) {
185         return true;
186     }
187     if (b.z > a.z) {
188         return false;
189     }
190     return false;
191 }
operator ==(const real3 & a,const real3 & b)192 CUDA_HOST_DEVICE bool operator==(const real3& a, const real3& b) {
193     return (a[0] == b[0]) && (a[1] == b[1]) && (a[2] == b[2]);
194     // return simd::IsEqual(a, b);
195 }
Round(const real3 & v)196 CUDA_HOST_DEVICE real3 Round(const real3& v) {
197     return simd::Round(v);
198 }
IsZero(const real3 & v)199 CUDA_HOST_DEVICE bool IsZero(const real3& v) {
200     return simd::IsZero(v, C_EPSILON);
201 }
OrthogonalVector(const real3 & v)202 CUDA_HOST_DEVICE real3 OrthogonalVector(const real3& v) {
203     real3 abs = Abs(v);
204     if (abs.x < abs.y) {
205         return abs.x < abs.z ? real3(0, v.z, -v.y) : real3(v.y, -v.x, 0);
206     } else {
207         return abs.y < abs.z ? real3(-v.z, 0, v.x) : real3(v.y, -v.x, 0);
208     }
209 }
UnitOrthogonalVector(const real3 & v)210 CUDA_HOST_DEVICE real3 UnitOrthogonalVector(const real3& v) {
211     return Normalize(OrthogonalVector(v));
212 }
213 
Sort(real & a,real & b,real & c)214 CUDA_HOST_DEVICE void Sort(real& a, real& b, real& c) {
215     if (a > b)
216         Swap(a, b);
217     if (b > c)
218         Swap(b, c);
219     if (a > b)
220         Swap(a, b);
221 }
222 
Print(real3 v,const char * name)223 CUDA_HOST_DEVICE void Print(real3 v, const char* name) {
224     printf("%s\n", name);
225     printf("%f %f %f\n", v[0], v[1], v[2]);
226 }
227 }
228 #endif
229