Back to home page

EIC code displayed by LXR

 
 

    


File indexing completed on 2026-04-09 07:49:33

0001 //
0002 // Copyright (c) 2019, NVIDIA CORPORATION. All rights reserved.
0003 //
0004 // Redistribution and use in source and binary forms, with or without
0005 // modification, are permitted provided that the following conditions
0006 // are met:
0007 //  * Redistributions of source code must retain the above copyright
0008 //    notice, this list of conditions and the following disclaimer.
0009 //  * Redistributions in binary form must reproduce the above copyright
0010 //    notice, this list of conditions and the following disclaimer in the
0011 //    documentation and/or other materials provided with the distribution.
0012 //  * Neither the name of NVIDIA CORPORATION nor the names of its
0013 //    contributors may be used to endorse or promote products derived
0014 //    from this software without specific prior written permission.
0015 //
0016 // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS ``AS IS'' AND ANY
0017 // EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
0018 // IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
0019 // PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL THE COPYRIGHT OWNER OR
0020 // CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
0021 // EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
0022 // PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
0023 // PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY
0024 // OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
0025 // (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
0026 // OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
0027 //
0028 
0029 
0030 #pragma once
0031 
0032 #if defined(__CUDACC__) || defined(__CUDABE__)
0033 #    define SUTIL_HOSTDEVICE __host__ __device__
0034 #    define SUTIL_INLINE __forceinline__
0035 #    define CONST_STATIC_INIT( ... )
0036 #else
0037 #    define SUTIL_HOSTDEVICE
0038 #    define SUTIL_INLINE inline
0039 #    define CONST_STATIC_INIT( ... ) = __VA_ARGS__
0040 #endif
0041 
0042 
0043 #include <vector_functions.h>
0044 #include <vector_types.h>
0045 
0046 
0047 #include <cmath>
0048 #include <cstdlib>
0049 
0050 #if defined(__CUDACC__) && (__CUDACC_VER_MAJOR__ >= 13)
0051 #    define LONGLONG4 longlong4_32a
0052 #    define ULONGLONG4 ulonglong4_32a
0053 #    define DOUBLE4 double4_32a
0054 #    define MAKE_LONGLONG4 make_longlong4_32a
0055 #    define MAKE_ULONGLONG4 make_ulonglong4_32a
0056 #else
0057 #    include <cuda_runtime_api.h>
0058 #    if (CUDART_VERSION >= 13000)
0059 #        define LONGLONG4 longlong4_32a
0060 #        define ULONGLONG4 ulonglong4_32a
0061 #        define DOUBLE4 double4_32a
0062 #        define MAKE_LONGLONG4 make_longlong4_32a
0063 #        define MAKE_ULONGLONG4 make_ulonglong4_32a
0064 #    else
0065 #        define LONGLONG4 longlong4
0066 #        define ULONGLONG4 ulonglong4
0067 #        define DOUBLE4 double4
0068 #        define MAKE_LONGLONG4 make_longlong4
0069 #        define MAKE_ULONGLONG4 make_ulonglong4
0070 #    endif
0071 #endif
0072 
0073 
0074 
0075 /* scalar functions used in vector functions */
0076 #ifndef M_PIf
0077 #define M_PIf       3.14159265358979323846f
0078 #endif
0079 #ifndef M_1_PIf
0080 #define M_1_PIf     0.318309886183790671538f
0081 #endif
0082 
0083 #ifndef M_SQRT2f
0084 #define M_SQRT2f  1.4142135623730951f
0085 #endif
0086 
0087 
0088 #if !defined(__CUDACC__)
0089 
0090 SUTIL_INLINE SUTIL_HOSTDEVICE int max(int a, int b)
0091 {
0092     return a > b ? a : b;
0093 }
0094 
0095 SUTIL_INLINE SUTIL_HOSTDEVICE int min(int a, int b)
0096 {
0097     return a < b ? a : b;
0098 }
0099 
0100 SUTIL_INLINE SUTIL_HOSTDEVICE long long max(long long a, long long b)
0101 {
0102     return a > b ? a : b;
0103 }
0104 
0105 SUTIL_INLINE SUTIL_HOSTDEVICE long long min(long long a, long long b)
0106 {
0107     return a < b ? a : b;
0108 }
0109 
0110 SUTIL_INLINE SUTIL_HOSTDEVICE unsigned int max(unsigned int a, unsigned int b)
0111 {
0112     return a > b ? a : b;
0113 }
0114 
0115 SUTIL_INLINE SUTIL_HOSTDEVICE unsigned int min(unsigned int a, unsigned int b)
0116 {
0117     return a < b ? a : b;
0118 }
0119 
0120 SUTIL_INLINE SUTIL_HOSTDEVICE unsigned long long max(unsigned long long a, unsigned long long b)
0121 {
0122     return a > b ? a : b;
0123 }
0124 
0125 SUTIL_INLINE SUTIL_HOSTDEVICE unsigned long long min(unsigned long long a, unsigned long long b)
0126 {
0127     return a < b ? a : b;
0128 }
0129 
0130 
0131 
0132 
0133 
0134 /**
0135 lerp
0136 ----
0137 
0138 For C++20 compilation have adopted the suggestion from Nicola Mori, although
0139 I did not succeed to reproduce the issue.
0140 
0141 notes/issues/cpp20_nicolamori_scuda_curand_math_lerp_conflict.rst
0142 
0143 **/
0144 
0145 #if __cplusplus <= 201703L
0146 SUTIL_INLINE SUTIL_HOSTDEVICE float lerp(const float a, const float b, const float t)
0147 {
0148   return a + t*(b-a);
0149 }
0150 #else
0151 using std::lerp;
0152 #endif
0153 
0154 
0155 
0156 /** bilerp */
0157 SUTIL_INLINE SUTIL_HOSTDEVICE float bilerp(const float x00, const float x10, const float x01, const float x11,
0158                                          const float u, const float v)
0159 {
0160   return lerp( lerp( x00, x10, u ), lerp( x01, x11, u ), v );
0161 }
0162 
0163 template <typename IntegerType>
0164 SUTIL_INLINE SUTIL_HOSTDEVICE IntegerType roundUp(IntegerType x, IntegerType y)
0165 {
0166     return ( ( x + y - 1 ) / y ) * y;
0167 }
0168 
0169 #endif
0170 
0171 /** clamp */
0172 SUTIL_INLINE SUTIL_HOSTDEVICE float clamp(const float f, const float a, const float b)
0173 {
0174   return fmaxf(a, fminf(f, b));
0175 }
0176 
0177 
0178 /* float2 functions */
0179 /******************************************************************************/
0180 
0181 /** additional constructors
0182 * @{
0183 */
0184 SUTIL_INLINE SUTIL_HOSTDEVICE float2 make_float2(const float s)
0185 {
0186   return make_float2(s, s);
0187 }
0188 SUTIL_INLINE SUTIL_HOSTDEVICE float2 make_float2(const int2& a)
0189 {
0190   return make_float2(float(a.x), float(a.y));
0191 }
0192 SUTIL_INLINE SUTIL_HOSTDEVICE float2 make_float2(const uint2& a)
0193 {
0194   return make_float2(float(a.x), float(a.y));
0195 }
0196 /** @} */
0197 
0198 /** negate */
0199 SUTIL_INLINE SUTIL_HOSTDEVICE float2 operator-(const float2& a)
0200 {
0201   return make_float2(-a.x, -a.y);
0202 }
0203 
0204 /** min
0205 * @{
0206 */
0207 SUTIL_INLINE SUTIL_HOSTDEVICE float2 fminf(const float2& a, const float2& b)
0208 {
0209   return make_float2(fminf(a.x,b.x), fminf(a.y,b.y));
0210 }
0211 SUTIL_INLINE SUTIL_HOSTDEVICE float fminf(const float2& a)
0212 {
0213   return fminf(a.x, a.y);
0214 }
0215 /** @} */
0216 
0217 /** max
0218 * @{
0219 */
0220 SUTIL_INLINE SUTIL_HOSTDEVICE float2 fmaxf(const float2& a, const float2& b)
0221 {
0222   return make_float2(fmaxf(a.x,b.x), fmaxf(a.y,b.y));
0223 }
0224 SUTIL_INLINE SUTIL_HOSTDEVICE float fmaxf(const float2& a)
0225 {
0226   return fmaxf(a.x, a.y);
0227 }
0228 /** @} */
0229 
0230 /** add
0231 * @{
0232 */
0233 SUTIL_INLINE SUTIL_HOSTDEVICE float2 operator+(const float2& a, const float2& b)
0234 {
0235   return make_float2(a.x + b.x, a.y + b.y);
0236 }
0237 SUTIL_INLINE SUTIL_HOSTDEVICE float2 operator+(const float2& a, const float b)
0238 {
0239   return make_float2(a.x + b, a.y + b);
0240 }
0241 SUTIL_INLINE SUTIL_HOSTDEVICE float2 operator+(const float a, const float2& b)
0242 {
0243   return make_float2(a + b.x, a + b.y);
0244 }
0245 SUTIL_INLINE SUTIL_HOSTDEVICE void operator+=(float2& a, const float2& b)
0246 {
0247   a.x += b.x; a.y += b.y;
0248 }
0249 /** @} */
0250 
0251 /** subtract
0252 * @{
0253 */
0254 SUTIL_INLINE SUTIL_HOSTDEVICE float2 operator-(const float2& a, const float2& b)
0255 {
0256   return make_float2(a.x - b.x, a.y - b.y);
0257 }
0258 SUTIL_INLINE SUTIL_HOSTDEVICE float2 operator-(const float2& a, const float b)
0259 {
0260   return make_float2(a.x - b, a.y - b);
0261 }
0262 SUTIL_INLINE SUTIL_HOSTDEVICE float2 operator-(const float a, const float2& b)
0263 {
0264   return make_float2(a - b.x, a - b.y);
0265 }
0266 SUTIL_INLINE SUTIL_HOSTDEVICE void operator-=(float2& a, const float2& b)
0267 {
0268   a.x -= b.x; a.y -= b.y;
0269 }
0270 /** @} */
0271 
0272 /** multiply
0273 * @{
0274 */
0275 SUTIL_INLINE SUTIL_HOSTDEVICE float2 operator*(const float2& a, const float2& b)
0276 {
0277   return make_float2(a.x * b.x, a.y * b.y);
0278 }
0279 SUTIL_INLINE SUTIL_HOSTDEVICE float2 operator*(const float2& a, const float s)
0280 {
0281   return make_float2(a.x * s, a.y * s);
0282 }
0283 SUTIL_INLINE SUTIL_HOSTDEVICE float2 operator*(const float s, const float2& a)
0284 {
0285   return make_float2(a.x * s, a.y * s);
0286 }
0287 SUTIL_INLINE SUTIL_HOSTDEVICE void operator*=(float2& a, const float2& s)
0288 {
0289   a.x *= s.x; a.y *= s.y;
0290 }
0291 SUTIL_INLINE SUTIL_HOSTDEVICE void operator*=(float2& a, const float s)
0292 {
0293   a.x *= s; a.y *= s;
0294 }
0295 /** @} */
0296 
0297 /** divide
0298 * @{
0299 */
0300 SUTIL_INLINE SUTIL_HOSTDEVICE float2 operator/(const float2& a, const float2& b)
0301 {
0302   return make_float2(a.x / b.x, a.y / b.y);
0303 }
0304 SUTIL_INLINE SUTIL_HOSTDEVICE float2 operator/(const float2& a, const float s)
0305 {
0306   float inv = 1.0f / s;
0307   return a * inv;
0308 }
0309 SUTIL_INLINE SUTIL_HOSTDEVICE float2 operator/(const float s, const float2& a)
0310 {
0311   return make_float2( s/a.x, s/a.y );
0312 }
0313 SUTIL_INLINE SUTIL_HOSTDEVICE void operator/=(float2& a, const float s)
0314 {
0315   float inv = 1.0f / s;
0316   a *= inv;
0317 }
0318 /** @} */
0319 
0320 /** lerp */
0321 SUTIL_INLINE SUTIL_HOSTDEVICE float2 lerp(const float2& a, const float2& b, const float t)
0322 {
0323   return a + t*(b-a);
0324 }
0325 
0326 /** bilerp */
0327 SUTIL_INLINE SUTIL_HOSTDEVICE float2 bilerp(const float2& x00, const float2& x10, const float2& x01, const float2& x11,
0328                                           const float u, const float v)
0329 {
0330   return lerp( lerp( x00, x10, u ), lerp( x01, x11, u ), v );
0331 }
0332 
0333 /** clamp
0334 * @{
0335 */
0336 SUTIL_INLINE SUTIL_HOSTDEVICE float2 clamp(const float2& v, const float a, const float b)
0337 {
0338   return make_float2(clamp(v.x, a, b), clamp(v.y, a, b));
0339 }
0340 
0341 SUTIL_INLINE SUTIL_HOSTDEVICE float2 clamp(const float2& v, const float2& a, const float2& b)
0342 {
0343   return make_float2(clamp(v.x, a.x, b.x), clamp(v.y, a.y, b.y));
0344 }
0345 /** @} */
0346 
0347 /** dot product */
0348 SUTIL_INLINE SUTIL_HOSTDEVICE float dot(const float2& a, const float2& b)
0349 {
0350   return a.x * b.x + a.y * b.y;
0351 }
0352 
0353 /** length */
0354 SUTIL_INLINE SUTIL_HOSTDEVICE float length(const float2& v)
0355 {
0356   return sqrtf(dot(v, v));
0357 }
0358 
0359 /** normalize */
0360 SUTIL_INLINE SUTIL_HOSTDEVICE float2 normalize(const float2& v)
0361 {
0362   float invLen = 1.0f / sqrtf(dot(v, v));
0363   return v * invLen;
0364 }
0365 
0366 /** floor */
0367 SUTIL_INLINE SUTIL_HOSTDEVICE float2 floor(const float2& v)
0368 {
0369   return make_float2(::floorf(v.x), ::floorf(v.y));
0370 }
0371 
0372 /** reflect */
0373 SUTIL_INLINE SUTIL_HOSTDEVICE float2 reflect(const float2& i, const float2& n)
0374 {
0375   return i - 2.0f * n * dot(n,i);
0376 }
0377 
0378 /** Faceforward
0379 * Returns N if dot(i, nref) > 0; else -N;
0380 * Typical usage is N = faceforward(N, -ray.dir, N);
0381 * Note that this is opposite of what faceforward does in Cg and GLSL */
0382 SUTIL_INLINE SUTIL_HOSTDEVICE float2 faceforward(const float2& n, const float2& i, const float2& nref)
0383 {
0384   return n * copysignf( 1.0f, dot(i, nref) );
0385 }
0386 
0387 /** exp */
0388 SUTIL_INLINE SUTIL_HOSTDEVICE float2 expf(const float2& v)
0389 {
0390   return make_float2(::expf(v.x), ::expf(v.y));
0391 }
0392 
0393 /** If used on the device, this could place the the 'v' in local memory */
0394 SUTIL_INLINE SUTIL_HOSTDEVICE float getByIndex(const float2& v, int i)
0395 {
0396   return ((float*)(&v))[i];
0397 }
0398 
0399 /** If used on the device, this could place the the 'v' in local memory */
0400 SUTIL_INLINE SUTIL_HOSTDEVICE void setByIndex(float2& v, int i, float x)
0401 {
0402   ((float*)(&v))[i] = x;
0403 }
0404 
0405 
0406 /* float3 functions */
0407 /******************************************************************************/
0408 
0409 /** additional constructors
0410 * @{
0411 */
0412 SUTIL_INLINE SUTIL_HOSTDEVICE float3 make_float3(const float s)
0413 {
0414   return make_float3(s, s, s);
0415 }
0416 SUTIL_INLINE SUTIL_HOSTDEVICE float3 make_float3(const float2& a)
0417 {
0418   return make_float3(a.x, a.y, 0.0f);
0419 }
0420 SUTIL_INLINE SUTIL_HOSTDEVICE float3 make_float3(const int3& a)
0421 {
0422   return make_float3(float(a.x), float(a.y), float(a.z));
0423 }
0424 SUTIL_INLINE SUTIL_HOSTDEVICE float3 make_float3(const uint3& a)
0425 {
0426   return make_float3(float(a.x), float(a.y), float(a.z));
0427 }
0428 /** @} */
0429 
0430 /** negate */
0431 SUTIL_INLINE SUTIL_HOSTDEVICE float3 operator-(const float3& a)
0432 {
0433   return make_float3(-a.x, -a.y, -a.z);
0434 }
0435 
0436 /** min
0437 * @{
0438 */
0439 SUTIL_INLINE SUTIL_HOSTDEVICE float3 fminf(const float3& a, const float3& b)
0440 {
0441   return make_float3(fminf(a.x,b.x), fminf(a.y,b.y), fminf(a.z,b.z));
0442 }
0443 SUTIL_INLINE SUTIL_HOSTDEVICE float fminf(const float3& a)
0444 {
0445   return fminf(fminf(a.x, a.y), a.z);
0446 }
0447 /** @} */
0448 
0449 /** max
0450 * @{
0451 */
0452 SUTIL_INLINE SUTIL_HOSTDEVICE float3 fmaxf(const float3& a, const float3& b)
0453 {
0454   return make_float3(fmaxf(a.x,b.x), fmaxf(a.y,b.y), fmaxf(a.z,b.z));
0455 }
0456 SUTIL_INLINE SUTIL_HOSTDEVICE float fmaxf(const float3& a)
0457 {
0458   return fmaxf(fmaxf(a.x, a.y), a.z);
0459 }
0460 /** @} */
0461 
0462 /** add
0463 * @{
0464 */
0465 SUTIL_INLINE SUTIL_HOSTDEVICE float3 operator+(const float3& a, const float3& b)
0466 {
0467   return make_float3(a.x + b.x, a.y + b.y, a.z + b.z);
0468 }
0469 SUTIL_INLINE SUTIL_HOSTDEVICE float3 operator+(const float3& a, const float b)
0470 {
0471   return make_float3(a.x + b, a.y + b, a.z + b);
0472 }
0473 SUTIL_INLINE SUTIL_HOSTDEVICE float3 operator+(const float a, const float3& b)
0474 {
0475   return make_float3(a + b.x, a + b.y, a + b.z);
0476 }
0477 SUTIL_INLINE SUTIL_HOSTDEVICE void operator+=(float3& a, const float3& b)
0478 {
0479   a.x += b.x; a.y += b.y; a.z += b.z;
0480 }
0481 /** @} */
0482 
0483 /** subtract
0484 * @{
0485 */
0486 SUTIL_INLINE SUTIL_HOSTDEVICE float3 operator-(const float3& a, const float3& b)
0487 {
0488   return make_float3(a.x - b.x, a.y - b.y, a.z - b.z);
0489 }
0490 SUTIL_INLINE SUTIL_HOSTDEVICE float3 operator-(const float3& a, const float b)
0491 {
0492   return make_float3(a.x - b, a.y - b, a.z - b);
0493 }
0494 SUTIL_INLINE SUTIL_HOSTDEVICE float3 operator-(const float a, const float3& b)
0495 {
0496   return make_float3(a - b.x, a - b.y, a - b.z);
0497 }
0498 SUTIL_INLINE SUTIL_HOSTDEVICE void operator-=(float3& a, const float3& b)
0499 {
0500   a.x -= b.x; a.y -= b.y; a.z -= b.z;
0501 }
0502 /** @} */
0503 
0504 /** multiply
0505 * @{
0506 */
0507 SUTIL_INLINE SUTIL_HOSTDEVICE float3 operator*(const float3& a, const float3& b)
0508 {
0509   return make_float3(a.x * b.x, a.y * b.y, a.z * b.z);
0510 }
0511 SUTIL_INLINE SUTIL_HOSTDEVICE float3 operator*(const float3& a, const float s)
0512 {
0513   return make_float3(a.x * s, a.y * s, a.z * s);
0514 }
0515 SUTIL_INLINE SUTIL_HOSTDEVICE float3 operator*(const float s, const float3& a)
0516 {
0517   return make_float3(a.x * s, a.y * s, a.z * s);
0518 }
0519 SUTIL_INLINE SUTIL_HOSTDEVICE void operator*=(float3& a, const float3& s)
0520 {
0521   a.x *= s.x; a.y *= s.y; a.z *= s.z;
0522 }
0523 SUTIL_INLINE SUTIL_HOSTDEVICE void operator*=(float3& a, const float s)
0524 {
0525   a.x *= s; a.y *= s; a.z *= s;
0526 }
0527 /** @} */
0528 
0529 /** divide
0530 * @{
0531 */
0532 SUTIL_INLINE SUTIL_HOSTDEVICE float3 operator/(const float3& a, const float3& b)
0533 {
0534   return make_float3(a.x / b.x, a.y / b.y, a.z / b.z);
0535 }
0536 SUTIL_INLINE SUTIL_HOSTDEVICE float3 operator/(const float3& a, const float s)
0537 {
0538   float inv = 1.0f / s;
0539   return a * inv;
0540 }
0541 SUTIL_INLINE SUTIL_HOSTDEVICE float3 operator/(const float s, const float3& a)
0542 {
0543   return make_float3( s/a.x, s/a.y, s/a.z );
0544 }
0545 SUTIL_INLINE SUTIL_HOSTDEVICE void operator/=(float3& a, const float s)
0546 {
0547   float inv = 1.0f / s;
0548   a *= inv;
0549 }
0550 /** @} */
0551 
0552 /** lerp */
0553 SUTIL_INLINE SUTIL_HOSTDEVICE float3 lerp(const float3& a, const float3& b, const float t)
0554 {
0555   return a + t*(b-a);
0556 }
0557 
0558 /** bilerp */
0559 SUTIL_INLINE SUTIL_HOSTDEVICE float3 bilerp(const float3& x00, const float3& x10, const float3& x01, const float3& x11,
0560                                           const float u, const float v)
0561 {
0562   return lerp( lerp( x00, x10, u ), lerp( x01, x11, u ), v );
0563 }
0564 
0565 /** clamp
0566 * @{
0567 */
0568 SUTIL_INLINE SUTIL_HOSTDEVICE float3 clamp(const float3& v, const float a, const float b)
0569 {
0570   return make_float3(clamp(v.x, a, b), clamp(v.y, a, b), clamp(v.z, a, b));
0571 }
0572 
0573 SUTIL_INLINE SUTIL_HOSTDEVICE float3 clamp(const float3& v, const float3& a, const float3& b)
0574 {
0575   return make_float3(clamp(v.x, a.x, b.x), clamp(v.y, a.y, b.y), clamp(v.z, a.z, b.z));
0576 }
0577 /** @} */
0578 
0579 /** dot product */
0580 SUTIL_INLINE SUTIL_HOSTDEVICE float dot(const float3& a, const float3& b)
0581 {
0582   return a.x * b.x + a.y * b.y + a.z * b.z;
0583 }
0584 
0585 /** cross product */
0586 SUTIL_INLINE SUTIL_HOSTDEVICE float3 cross(const float3& a, const float3& b)
0587 {
0588   return make_float3(a.y*b.z - a.z*b.y, a.z*b.x - a.x*b.z, a.x*b.y - a.y*b.x);
0589 }
0590 
0591 /** length */
0592 SUTIL_INLINE SUTIL_HOSTDEVICE float length(const float3& v)
0593 {
0594   return sqrtf(dot(v, v));
0595 }
0596 
0597 /** normalize */
0598 SUTIL_INLINE SUTIL_HOSTDEVICE float3 normalize(const float3& v)
0599 {
0600   float invLen = 1.0f / sqrtf(dot(v, v));
0601   return v * invLen;
0602 }
0603 
0604 SUTIL_INLINE SUTIL_HOSTDEVICE float normalize_cost(const float3& v)  // formerly normalize_z,  CLHEP ThreeVector calls this cosTheta
0605 {
0606   return v.z / sqrtf(dot(v, v));
0607 }
0608 
0609 
0610 /**
0611 normalize_fphi
0612 --------------
0613 
0614 atan2f range is -pi to pi, so add pi, giving range 0 to 2pi
0615 which is then normalized to give fphi in range 0:1
0616 
0617 Note discontinuity of phi close to [-1,0,0] flipping between pi and -pi,
0618 
0619     In [4]: np.arctan2(+0.00000001, -1)
0620     Out[4]: np.float64(3.141592643589793)
0621 
0622     In [5]: np.arctan2(-0.00000001, -1)
0623     Out[5]: np.float64(-3.141592643589793)
0624 
0625 Which corresponds to fphi flipping between 0 and 1::
0626 
0627     In [6]: (np.arctan2(-0.00000001, -1) + np.pi)/(2*np.pi)
0628     Out[6]: np.float64(1.591549421246358e-09)
0629 
0630     In [7]: (np.arctan2(+0.00000001, -1) + np.pi)/(2*np.pi)
0631     Out[7]: np.float64(0.9999999984084506)
0632 
0633 No such issue at [1,0,0] where fphi close to 0.5::
0634 
0635     In [8]: (np.arctan2(+0.00000001, 1) + np.pi)/(2*np.pi)
0636     Out[8]: np.float64(0.5000000015915494)
0637 
0638     In [9]: (np.arctan2(-0.00000001, 1) + np.pi)/(2*np.pi)
0639     Out[9]: np.float64(0.49999999840845055)
0640 
0641 
0642 **/
0643 
0644 
0645 SUTIL_INLINE SUTIL_HOSTDEVICE float normalize_fphi(const float3& v)
0646 {
0647   return (atan2f(v.y, v.x) + M_PIf) / (2.0f * M_PIf);
0648 }
0649 
0650 SUTIL_INLINE SUTIL_HOSTDEVICE float phi_from_fphi( float fphi )
0651 {
0652    // recover phi angle in range -pi to pi from fphi in range 0:1
0653    return ( fphi * 2.0f - 1.f ) * M_PIf ;
0654 }
0655 
0656 
0657 
0658 /** floor */
0659 SUTIL_INLINE SUTIL_HOSTDEVICE float3 floor(const float3& v)
0660 {
0661   return make_float3(::floorf(v.x), ::floorf(v.y), ::floorf(v.z));
0662 }
0663 
0664 /** reflect */
0665 SUTIL_INLINE SUTIL_HOSTDEVICE float3 reflect(const float3& i, const float3& n)
0666 {
0667   return i - 2.0f * n * dot(n,i);
0668 }
0669 
0670 /** Faceforward
0671 * Returns N if dot(i, nref) > 0; else -N;
0672 * Typical usage is N = faceforward(N, -ray.dir, N);
0673 * Note that this is opposite of what faceforward does in Cg and GLSL */
0674 SUTIL_INLINE SUTIL_HOSTDEVICE float3 faceforward(const float3& n, const float3& i, const float3& nref)
0675 {
0676   return n * copysignf( 1.0f, dot(i, nref) );
0677 }
0678 
0679 /** exp */
0680 SUTIL_INLINE SUTIL_HOSTDEVICE float3 expf(const float3& v)
0681 {
0682   return make_float3(::expf(v.x), ::expf(v.y), ::expf(v.z));
0683 }
0684 
0685 /** If used on the device, this could place the the 'v' in local memory */
0686 SUTIL_INLINE SUTIL_HOSTDEVICE float getByIndex(const float3& v, int i)
0687 {
0688   return ((float*)(&v))[i];
0689 }
0690 
0691 /** If used on the device, this could place the the 'v' in local memory */
0692 SUTIL_INLINE SUTIL_HOSTDEVICE void setByIndex(float3& v, int i, float x)
0693 {
0694   ((float*)(&v))[i] = x;
0695 }
0696 
0697 /* float4 functions */
0698 /******************************************************************************/
0699 
0700 /** additional constructors
0701 * @{
0702 */
0703 SUTIL_INLINE SUTIL_HOSTDEVICE float4 make_float4(const float s)
0704 {
0705   return make_float4(s, s, s, s);
0706 }
0707 SUTIL_INLINE SUTIL_HOSTDEVICE float4 make_float4(const float3& a)
0708 {
0709   return make_float4(a.x, a.y, a.z, 0.0f);
0710 }
0711 SUTIL_INLINE SUTIL_HOSTDEVICE float4 make_float4(const int4& a)
0712 {
0713   return make_float4(float(a.x), float(a.y), float(a.z), float(a.w));
0714 }
0715 SUTIL_INLINE SUTIL_HOSTDEVICE float4 make_float4(const uint4& a)
0716 {
0717   return make_float4(float(a.x), float(a.y), float(a.z), float(a.w));
0718 }
0719 /** @} */
0720 
0721 /** negate */
0722 SUTIL_INLINE SUTIL_HOSTDEVICE float4 operator-(const float4& a)
0723 {
0724   return make_float4(-a.x, -a.y, -a.z, -a.w);
0725 }
0726 
0727 /** min
0728 * @{
0729 */
0730 SUTIL_INLINE SUTIL_HOSTDEVICE float4 fminf(const float4& a, const float4& b)
0731 {
0732   return make_float4(fminf(a.x,b.x), fminf(a.y,b.y), fminf(a.z,b.z), fminf(a.w,b.w));
0733 }
0734 SUTIL_INLINE SUTIL_HOSTDEVICE float fminf(const float4& a)
0735 {
0736   return fminf(fminf(a.x, a.y), fminf(a.z, a.w));
0737 }
0738 /** @} */
0739 
0740 /** max
0741 * @{
0742 */
0743 SUTIL_INLINE SUTIL_HOSTDEVICE float4 fmaxf(const float4& a, const float4& b)
0744 {
0745   return make_float4(fmaxf(a.x,b.x), fmaxf(a.y,b.y), fmaxf(a.z,b.z), fmaxf(a.w,b.w));
0746 }
0747 SUTIL_INLINE SUTIL_HOSTDEVICE float fmaxf(const float4& a)
0748 {
0749   return fmaxf(fmaxf(a.x, a.y), fmaxf(a.z, a.w));
0750 }
0751 /** @} */
0752 
0753 /** add
0754 * @{
0755 */
0756 SUTIL_INLINE SUTIL_HOSTDEVICE float4 operator+(const float4& a, const float4& b)
0757 {
0758   return make_float4(a.x + b.x, a.y + b.y, a.z + b.z,  a.w + b.w);
0759 }
0760 SUTIL_INLINE SUTIL_HOSTDEVICE float4 operator+(const float4& a, const float b)
0761 {
0762   return make_float4(a.x + b, a.y + b, a.z + b,  a.w + b);
0763 }
0764 SUTIL_INLINE SUTIL_HOSTDEVICE float4 operator+(const float a, const float4& b)
0765 {
0766   return make_float4(a + b.x, a + b.y, a + b.z,  a + b.w);
0767 }
0768 SUTIL_INLINE SUTIL_HOSTDEVICE void operator+=(float4& a, const float4& b)
0769 {
0770   a.x += b.x; a.y += b.y; a.z += b.z; a.w += b.w;
0771 }
0772 /** @} */
0773 
0774 /** subtract
0775 * @{
0776 */
0777 SUTIL_INLINE SUTIL_HOSTDEVICE float4 operator-(const float4& a, const float4& b)
0778 {
0779   return make_float4(a.x - b.x, a.y - b.y, a.z - b.z,  a.w - b.w);
0780 }
0781 SUTIL_INLINE SUTIL_HOSTDEVICE float4 operator-(const float4& a, const float b)
0782 {
0783   return make_float4(a.x - b, a.y - b, a.z - b,  a.w - b);
0784 }
0785 SUTIL_INLINE SUTIL_HOSTDEVICE float4 operator-(const float a, const float4& b)
0786 {
0787   return make_float4(a - b.x, a - b.y, a - b.z,  a - b.w);
0788 }
0789 SUTIL_INLINE SUTIL_HOSTDEVICE void operator-=(float4& a, const float4& b)
0790 {
0791   a.x -= b.x; a.y -= b.y; a.z -= b.z; a.w -= b.w;
0792 }
0793 /** @} */
0794 
0795 /** multiply
0796 * @{
0797 */
0798 SUTIL_INLINE SUTIL_HOSTDEVICE float4 operator*(const float4& a, const float4& s)
0799 {
0800   return make_float4(a.x * s.x, a.y * s.y, a.z * s.z, a.w * s.w);
0801 }
0802 SUTIL_INLINE SUTIL_HOSTDEVICE float4 operator*(const float4& a, const float s)
0803 {
0804   return make_float4(a.x * s, a.y * s, a.z * s, a.w * s);
0805 }
0806 SUTIL_INLINE SUTIL_HOSTDEVICE float4 operator*(const float s, const float4& a)
0807 {
0808   return make_float4(a.x * s, a.y * s, a.z * s, a.w * s);
0809 }
0810 SUTIL_INLINE SUTIL_HOSTDEVICE void operator*=(float4& a, const float4& s)
0811 {
0812   a.x *= s.x; a.y *= s.y; a.z *= s.z; a.w *= s.w;
0813 }
0814 SUTIL_INLINE SUTIL_HOSTDEVICE void operator*=(float4& a, const float s)
0815 {
0816   a.x *= s; a.y *= s; a.z *= s; a.w *= s;
0817 }
0818 /** @} */
0819 
0820 /** divide
0821 * @{
0822 */
0823 SUTIL_INLINE SUTIL_HOSTDEVICE float4 operator/(const float4& a, const float4& b)
0824 {
0825   return make_float4(a.x / b.x, a.y / b.y, a.z / b.z, a.w / b.w);
0826 }
0827 SUTIL_INLINE SUTIL_HOSTDEVICE float4 operator/(const float4& a, const float s)
0828 {
0829   float inv = 1.0f / s;
0830   return a * inv;
0831 }
0832 SUTIL_INLINE SUTIL_HOSTDEVICE float4 operator/(const float s, const float4& a)
0833 {
0834   return make_float4( s/a.x, s/a.y, s/a.z, s/a.w );
0835 }
0836 SUTIL_INLINE SUTIL_HOSTDEVICE void operator/=(float4& a, const float s)
0837 {
0838   float inv = 1.0f / s;
0839   a *= inv;
0840 }
0841 /** @} */
0842 
0843 /** lerp */
0844 SUTIL_INLINE SUTIL_HOSTDEVICE float4 lerp(const float4& a, const float4& b, const float t)
0845 {
0846   return a + t*(b-a);
0847 }
0848 
0849 /** bilerp */
0850 SUTIL_INLINE SUTIL_HOSTDEVICE float4 bilerp(const float4& x00, const float4& x10, const float4& x01, const float4& x11,
0851                                           const float u, const float v)
0852 {
0853   return lerp( lerp( x00, x10, u ), lerp( x01, x11, u ), v );
0854 }
0855 
0856 /** clamp
0857 * @{
0858 */
0859 SUTIL_INLINE SUTIL_HOSTDEVICE float4 clamp(const float4& v, const float a, const float b)
0860 {
0861   return make_float4(clamp(v.x, a, b), clamp(v.y, a, b), clamp(v.z, a, b), clamp(v.w, a, b));
0862 }
0863 
0864 SUTIL_INLINE SUTIL_HOSTDEVICE float4 clamp(const float4& v, const float4& a, const float4& b)
0865 {
0866   return make_float4(clamp(v.x, a.x, b.x), clamp(v.y, a.y, b.y), clamp(v.z, a.z, b.z), clamp(v.w, a.w, b.w));
0867 }
0868 /** @} */
0869 
0870 /** dot product */
0871 SUTIL_INLINE SUTIL_HOSTDEVICE float dot(const float4& a, const float4& b)
0872 {
0873   return a.x * b.x + a.y * b.y + a.z * b.z + a.w * b.w;
0874 }
0875 
0876 /** length */
0877 SUTIL_INLINE SUTIL_HOSTDEVICE float length(const float4& r)
0878 {
0879   return sqrtf(dot(r, r));
0880 }
0881 
0882 /** normalize */
0883 SUTIL_INLINE SUTIL_HOSTDEVICE float4 normalize(const float4& v)
0884 {
0885   float invLen = 1.0f / sqrtf(dot(v, v));
0886   return v * invLen;
0887 }
0888 
0889 /** floor */
0890 SUTIL_INLINE SUTIL_HOSTDEVICE float4 floor(const float4& v)
0891 {
0892   return make_float4(::floorf(v.x), ::floorf(v.y), ::floorf(v.z), ::floorf(v.w));
0893 }
0894 
0895 /** reflect */
0896 SUTIL_INLINE SUTIL_HOSTDEVICE float4 reflect(const float4& i, const float4& n)
0897 {
0898   return i - 2.0f * n * dot(n,i);
0899 }
0900 
0901 /**
0902 * Faceforward
0903 * Returns N if dot(i, nref) > 0; else -N;
0904 * Typical usage is N = faceforward(N, -ray.dir, N);
0905 * Note that this is opposite of what faceforward does in Cg and GLSL
0906 */
0907 SUTIL_INLINE SUTIL_HOSTDEVICE float4 faceforward(const float4& n, const float4& i, const float4& nref)
0908 {
0909   return n * copysignf( 1.0f, dot(i, nref) );
0910 }
0911 
0912 /** exp */
0913 SUTIL_INLINE SUTIL_HOSTDEVICE float4 expf(const float4& v)
0914 {
0915   return make_float4(::expf(v.x), ::expf(v.y), ::expf(v.z), ::expf(v.w));
0916 }
0917 
0918 /** If used on the device, this could place the the 'v' in local memory */
0919 SUTIL_INLINE SUTIL_HOSTDEVICE float getByIndex(const float4& v, int i)
0920 {
0921   return ((float*)(&v))[i];
0922 }
0923 
0924 /** If used on the device, this could place the the 'v' in local memory */
0925 SUTIL_INLINE SUTIL_HOSTDEVICE void setByIndex(float4& v, int i, float x)
0926 {
0927   ((float*)(&v))[i] = x;
0928 }
0929 
0930 
0931 /* int functions */
0932 /******************************************************************************/
0933 
0934 /** clamp */
0935 SUTIL_INLINE SUTIL_HOSTDEVICE int clamp(const int f, const int a, const int b)
0936 {
0937   return max(a, min(f, b));
0938 }
0939 
0940 /** If used on the device, this could place the the 'v' in local memory */
0941 SUTIL_INLINE SUTIL_HOSTDEVICE int getByIndex(const int1& v, int i)
0942 {
0943   return ((int*)(&v))[i];
0944 }
0945 
0946 /** If used on the device, this could place the the 'v' in local memory */
0947 SUTIL_INLINE SUTIL_HOSTDEVICE void setByIndex(int1& v, int i, int x)
0948 {
0949   ((int*)(&v))[i] = x;
0950 }
0951 
0952 
0953 /* int2 functions */
0954 /******************************************************************************/
0955 
0956 /** additional constructors
0957 * @{
0958 */
0959 SUTIL_INLINE SUTIL_HOSTDEVICE int2 make_int2(const int s)
0960 {
0961   return make_int2(s, s);
0962 }
0963 SUTIL_INLINE SUTIL_HOSTDEVICE int2 make_int2(const float2& a)
0964 {
0965   return make_int2(int(a.x), int(a.y));
0966 }
0967 /** @} */
0968 
0969 /** negate */
0970 SUTIL_INLINE SUTIL_HOSTDEVICE int2 operator-(const int2& a)
0971 {
0972   return make_int2(-a.x, -a.y);
0973 }
0974 
0975 /** min */
0976 SUTIL_INLINE SUTIL_HOSTDEVICE int2 min(const int2& a, const int2& b)
0977 {
0978   return make_int2(min(a.x,b.x), min(a.y,b.y));
0979 }
0980 
0981 /** max */
0982 SUTIL_INLINE SUTIL_HOSTDEVICE int2 max(const int2& a, const int2& b)
0983 {
0984   return make_int2(max(a.x,b.x), max(a.y,b.y));
0985 }
0986 
0987 /** add
0988 * @{
0989 */
0990 SUTIL_INLINE SUTIL_HOSTDEVICE int2 operator+(const int2& a, const int2& b)
0991 {
0992   return make_int2(a.x + b.x, a.y + b.y);
0993 }
0994 SUTIL_INLINE SUTIL_HOSTDEVICE void operator+=(int2& a, const int2& b)
0995 {
0996   a.x += b.x; a.y += b.y;
0997 }
0998 /** @} */
0999 
1000 /** subtract
1001 * @{
1002 */
1003 SUTIL_INLINE SUTIL_HOSTDEVICE int2 operator-(const int2& a, const int2& b)
1004 {
1005   return make_int2(a.x - b.x, a.y - b.y);
1006 }
1007 SUTIL_INLINE SUTIL_HOSTDEVICE int2 operator-(const int2& a, const int b)
1008 {
1009   return make_int2(a.x - b, a.y - b);
1010 }
1011 SUTIL_INLINE SUTIL_HOSTDEVICE void operator-=(int2& a, const int2& b)
1012 {
1013   a.x -= b.x; a.y -= b.y;
1014 }
1015 /** @} */
1016 
1017 /** multiply
1018 * @{
1019 */
1020 SUTIL_INLINE SUTIL_HOSTDEVICE int2 operator*(const int2& a, const int2& b)
1021 {
1022   return make_int2(a.x * b.x, a.y * b.y);
1023 }
1024 SUTIL_INLINE SUTIL_HOSTDEVICE int2 operator*(const int2& a, const int s)
1025 {
1026   return make_int2(a.x * s, a.y * s);
1027 }
1028 SUTIL_INLINE SUTIL_HOSTDEVICE int2 operator*(const int s, const int2& a)
1029 {
1030   return make_int2(a.x * s, a.y * s);
1031 }
1032 SUTIL_INLINE SUTIL_HOSTDEVICE void operator*=(int2& a, const int s)
1033 {
1034   a.x *= s; a.y *= s;
1035 }
1036 /** @} */
1037 
1038 /** clamp
1039 * @{
1040 */
1041 SUTIL_INLINE SUTIL_HOSTDEVICE int2 clamp(const int2& v, const int a, const int b)
1042 {
1043   return make_int2(clamp(v.x, a, b), clamp(v.y, a, b));
1044 }
1045 
1046 SUTIL_INLINE SUTIL_HOSTDEVICE int2 clamp(const int2& v, const int2& a, const int2& b)
1047 {
1048   return make_int2(clamp(v.x, a.x, b.x), clamp(v.y, a.y, b.y));
1049 }
1050 /** @} */
1051 
1052 /** equality
1053 * @{
1054 */
1055 SUTIL_INLINE SUTIL_HOSTDEVICE bool operator==(const int2& a, const int2& b)
1056 {
1057   return a.x == b.x && a.y == b.y;
1058 }
1059 
1060 SUTIL_INLINE SUTIL_HOSTDEVICE bool operator!=(const int2& a, const int2& b)
1061 {
1062   return a.x != b.x || a.y != b.y;
1063 }
1064 /** @} */
1065 
1066 /** If used on the device, this could place the the 'v' in local memory */
1067 SUTIL_INLINE SUTIL_HOSTDEVICE int getByIndex(const int2& v, int i)
1068 {
1069   return ((int*)(&v))[i];
1070 }
1071 
1072 /** If used on the device, this could place the the 'v' in local memory */
1073 SUTIL_INLINE SUTIL_HOSTDEVICE void setByIndex(int2& v, int i, int x)
1074 {
1075   ((int*)(&v))[i] = x;
1076 }
1077 
1078 
1079 /* int3 functions */
1080 /******************************************************************************/
1081 
1082 /** additional constructors
1083 * @{
1084 */
1085 SUTIL_INLINE SUTIL_HOSTDEVICE int3 make_int3(const int s)
1086 {
1087   return make_int3(s, s, s);
1088 }
1089 SUTIL_INLINE SUTIL_HOSTDEVICE int3 make_int3(const float3& a)
1090 {
1091   return make_int3(int(a.x), int(a.y), int(a.z));
1092 }
1093 /** @} */
1094 
1095 /** negate */
1096 SUTIL_INLINE SUTIL_HOSTDEVICE int3 operator-(const int3& a)
1097 {
1098   return make_int3(-a.x, -a.y, -a.z);
1099 }
1100 
1101 /** min */
1102 SUTIL_INLINE SUTIL_HOSTDEVICE int3 min(const int3& a, const int3& b)
1103 {
1104   return make_int3(min(a.x,b.x), min(a.y,b.y), min(a.z,b.z));
1105 }
1106 
1107 /** max */
1108 SUTIL_INLINE SUTIL_HOSTDEVICE int3 max(const int3& a, const int3& b)
1109 {
1110   return make_int3(max(a.x,b.x), max(a.y,b.y), max(a.z,b.z));
1111 }
1112 
1113 /** add
1114 * @{
1115 */
1116 SUTIL_INLINE SUTIL_HOSTDEVICE int3 operator+(const int3& a, const int3& b)
1117 {
1118   return make_int3(a.x + b.x, a.y + b.y, a.z + b.z);
1119 }
1120 SUTIL_INLINE SUTIL_HOSTDEVICE void operator+=(int3& a, const int3& b)
1121 {
1122   a.x += b.x; a.y += b.y; a.z += b.z;
1123 }
1124 /** @} */
1125 
1126 /** subtract
1127 * @{
1128 */
1129 SUTIL_INLINE SUTIL_HOSTDEVICE int3 operator-(const int3& a, const int3& b)
1130 {
1131   return make_int3(a.x - b.x, a.y - b.y, a.z - b.z);
1132 }
1133 
1134 SUTIL_INLINE SUTIL_HOSTDEVICE void operator-=(int3& a, const int3& b)
1135 {
1136   a.x -= b.x; a.y -= b.y; a.z -= b.z;
1137 }
1138 /** @} */
1139 
1140 /** multiply
1141 * @{
1142 */
1143 SUTIL_INLINE SUTIL_HOSTDEVICE int3 operator*(const int3& a, const int3& b)
1144 {
1145   return make_int3(a.x * b.x, a.y * b.y, a.z * b.z);
1146 }
1147 SUTIL_INLINE SUTIL_HOSTDEVICE int3 operator*(const int3& a, const int s)
1148 {
1149   return make_int3(a.x * s, a.y * s, a.z * s);
1150 }
1151 SUTIL_INLINE SUTIL_HOSTDEVICE int3 operator*(const int s, const int3& a)
1152 {
1153   return make_int3(a.x * s, a.y * s, a.z * s);
1154 }
1155 SUTIL_INLINE SUTIL_HOSTDEVICE void operator*=(int3& a, const int s)
1156 {
1157   a.x *= s; a.y *= s; a.z *= s;
1158 }
1159 /** @} */
1160 
1161 /** divide
1162 * @{
1163 */
1164 SUTIL_INLINE SUTIL_HOSTDEVICE int3 operator/(const int3& a, const int3& b)
1165 {
1166   return make_int3(a.x / b.x, a.y / b.y, a.z / b.z);
1167 }
1168 SUTIL_INLINE SUTIL_HOSTDEVICE int3 operator/(const int3& a, const int s)
1169 {
1170   return make_int3(a.x / s, a.y / s, a.z / s);
1171 }
1172 SUTIL_INLINE SUTIL_HOSTDEVICE int3 operator/(const int s, const int3& a)
1173 {
1174   return make_int3(s /a.x, s / a.y, s / a.z);
1175 }
1176 SUTIL_INLINE SUTIL_HOSTDEVICE void operator/=(int3& a, const int s)
1177 {
1178   a.x /= s; a.y /= s; a.z /= s;
1179 }
1180 /** @} */
1181 
1182 /** clamp
1183 * @{
1184 */
1185 SUTIL_INLINE SUTIL_HOSTDEVICE int3 clamp(const int3& v, const int a, const int b)
1186 {
1187   return make_int3(clamp(v.x, a, b), clamp(v.y, a, b), clamp(v.z, a, b));
1188 }
1189 
1190 SUTIL_INLINE SUTIL_HOSTDEVICE int3 clamp(const int3& v, const int3& a, const int3& b)
1191 {
1192   return make_int3(clamp(v.x, a.x, b.x), clamp(v.y, a.y, b.y), clamp(v.z, a.z, b.z));
1193 }
1194 /** @} */
1195 
1196 /** equality
1197 * @{
1198 */
1199 SUTIL_INLINE SUTIL_HOSTDEVICE bool operator==(const int3& a, const int3& b)
1200 {
1201   return a.x == b.x && a.y == b.y && a.z == b.z;
1202 }
1203 
1204 SUTIL_INLINE SUTIL_HOSTDEVICE bool operator!=(const int3& a, const int3& b)
1205 {
1206   return a.x != b.x || a.y != b.y || a.z != b.z;
1207 }
1208 /** @} */
1209 
1210 /** If used on the device, this could place the the 'v' in local memory */
1211 SUTIL_INLINE SUTIL_HOSTDEVICE int getByIndex(const int3& v, int i)
1212 {
1213   return ((int*)(&v))[i];
1214 }
1215 
1216 /** If used on the device, this could place the the 'v' in local memory */
1217 SUTIL_INLINE SUTIL_HOSTDEVICE void setByIndex(int3& v, int i, int x)
1218 {
1219   ((int*)(&v))[i] = x;
1220 }
1221 
1222 
1223 /* int4 functions */
1224 /******************************************************************************/
1225 
1226 /** additional constructors
1227 * @{
1228 */
1229 SUTIL_INLINE SUTIL_HOSTDEVICE int4 make_int4(const int s)
1230 {
1231   return make_int4(s, s, s, s);
1232 }
1233 SUTIL_INLINE SUTIL_HOSTDEVICE int4 make_int4(const float4& a)
1234 {
1235   return make_int4((int)a.x, (int)a.y, (int)a.z, (int)a.w);
1236 }
1237 /** @} */
1238 
1239 /** negate */
1240 SUTIL_INLINE SUTIL_HOSTDEVICE int4 operator-(const int4& a)
1241 {
1242   return make_int4(-a.x, -a.y, -a.z, -a.w);
1243 }
1244 
1245 /** min */
1246 SUTIL_INLINE SUTIL_HOSTDEVICE int4 min(const int4& a, const int4& b)
1247 {
1248   return make_int4(min(a.x,b.x), min(a.y,b.y), min(a.z,b.z), min(a.w,b.w));
1249 }
1250 
1251 /** max */
1252 SUTIL_INLINE SUTIL_HOSTDEVICE int4 max(const int4& a, const int4& b)
1253 {
1254   return make_int4(max(a.x,b.x), max(a.y,b.y), max(a.z,b.z), max(a.w,b.w));
1255 }
1256 
1257 /** add
1258 * @{
1259 */
1260 SUTIL_INLINE SUTIL_HOSTDEVICE int4 operator+(const int4& a, const int4& b)
1261 {
1262   return make_int4(a.x + b.x, a.y + b.y, a.z + b.z, a.w + b.w);
1263 }
1264 SUTIL_INLINE SUTIL_HOSTDEVICE void operator+=(int4& a, const int4& b)
1265 {
1266   a.x += b.x; a.y += b.y; a.z += b.z; a.w += b.w;
1267 }
1268 /** @} */
1269 
1270 /** subtract
1271 * @{
1272 */
1273 SUTIL_INLINE SUTIL_HOSTDEVICE int4 operator-(const int4& a, const int4& b)
1274 {
1275   return make_int4(a.x - b.x, a.y - b.y, a.z - b.z, a.w - b.w);
1276 }
1277 
1278 SUTIL_INLINE SUTIL_HOSTDEVICE void operator-=(int4& a, const int4& b)
1279 {
1280   a.x -= b.x; a.y -= b.y; a.z -= b.z; a.w -= b.w;
1281 }
1282 /** @} */
1283 
1284 /** multiply
1285 * @{
1286 */
1287 SUTIL_INLINE SUTIL_HOSTDEVICE int4 operator*(const int4& a, const int4& b)
1288 {
1289   return make_int4(a.x * b.x, a.y * b.y, a.z * b.z, a.w * b.w);
1290 }
1291 SUTIL_INLINE SUTIL_HOSTDEVICE int4 operator*(const int4& a, const int s)
1292 {
1293   return make_int4(a.x * s, a.y * s, a.z * s, a.w * s);
1294 }
1295 SUTIL_INLINE SUTIL_HOSTDEVICE int4 operator*(const int s, const int4& a)
1296 {
1297   return make_int4(a.x * s, a.y * s, a.z * s, a.w * s);
1298 }
1299 SUTIL_INLINE SUTIL_HOSTDEVICE void operator*=(int4& a, const int s)
1300 {
1301   a.x *= s; a.y *= s; a.z *= s; a.w *= s;
1302 }
1303 /** @} */
1304 
1305 /** divide
1306 * @{
1307 */
1308 SUTIL_INLINE SUTIL_HOSTDEVICE int4 operator/(const int4& a, const int4& b)
1309 {
1310   return make_int4(a.x / b.x, a.y / b.y, a.z / b.z, a.w / b.w);
1311 }
1312 SUTIL_INLINE SUTIL_HOSTDEVICE int4 operator/(const int4& a, const int s)
1313 {
1314   return make_int4(a.x / s, a.y / s, a.z / s, a.w / s);
1315 }
1316 SUTIL_INLINE SUTIL_HOSTDEVICE int4 operator/(const int s, const int4& a)
1317 {
1318   return make_int4(s / a.x, s / a.y, s / a.z, s / a.w);
1319 }
1320 SUTIL_INLINE SUTIL_HOSTDEVICE void operator/=(int4& a, const int s)
1321 {
1322   a.x /= s; a.y /= s; a.z /= s; a.w /= s;
1323 }
1324 /** @} */
1325 
1326 /** clamp
1327 * @{
1328 */
1329 SUTIL_INLINE SUTIL_HOSTDEVICE int4 clamp(const int4& v, const int a, const int b)
1330 {
1331   return make_int4(clamp(v.x, a, b), clamp(v.y, a, b), clamp(v.z, a, b), clamp(v.w, a, b));
1332 }
1333 
1334 SUTIL_INLINE SUTIL_HOSTDEVICE int4 clamp(const int4& v, const int4& a, const int4& b)
1335 {
1336   return make_int4(clamp(v.x, a.x, b.x), clamp(v.y, a.y, b.y), clamp(v.z, a.z, b.z), clamp(v.w, a.w, b.w));
1337 }
1338 /** @} */
1339 
1340 /** equality
1341 * @{
1342 */
1343 SUTIL_INLINE SUTIL_HOSTDEVICE bool operator==(const int4& a, const int4& b)
1344 {
1345   return a.x == b.x && a.y == b.y && a.z == b.z && a.w == b.w;
1346 }
1347 
1348 SUTIL_INLINE SUTIL_HOSTDEVICE bool operator!=(const int4& a, const int4& b)
1349 {
1350   return a.x != b.x || a.y != b.y || a.z != b.z || a.w != b.w;
1351 }
1352 /** @} */
1353 
1354 /** If used on the device, this could place the the 'v' in local memory */
1355 SUTIL_INLINE SUTIL_HOSTDEVICE int getByIndex(const int4& v, int i)
1356 {
1357   return ((int*)(&v))[i];
1358 }
1359 
1360 /** If used on the device, this could place the the 'v' in local memory */
1361 SUTIL_INLINE SUTIL_HOSTDEVICE void setByIndex(int4& v, int i, int x)
1362 {
1363   ((int*)(&v))[i] = x;
1364 }
1365 
1366 
1367 /* uint functions */
1368 /******************************************************************************/
1369 
1370 /** clamp */
1371 SUTIL_INLINE SUTIL_HOSTDEVICE unsigned int clamp(const unsigned int f, const unsigned int a, const unsigned int b)
1372 {
1373   return max(a, min(f, b));
1374 }
1375 
1376 /** If used on the device, this could place the the 'v' in local memory */
1377 SUTIL_INLINE SUTIL_HOSTDEVICE unsigned int getByIndex(const uint1& v, unsigned int i)
1378 {
1379   return ((unsigned int*)(&v))[i];
1380 }
1381 
1382 /** If used on the device, this could place the the 'v' in local memory */
1383 SUTIL_INLINE SUTIL_HOSTDEVICE void setByIndex(uint1& v, int i, unsigned int x)
1384 {
1385   ((unsigned int*)(&v))[i] = x;
1386 }
1387 
1388 
1389 /* uint2 functions */
1390 /******************************************************************************/
1391 
1392 /** additional constructors
1393 * @{
1394 */
1395 SUTIL_INLINE SUTIL_HOSTDEVICE uint2 make_uint2(const unsigned int s)
1396 {
1397   return make_uint2(s, s);
1398 }
1399 SUTIL_INLINE SUTIL_HOSTDEVICE uint2 make_uint2(const float2& a)
1400 {
1401   return make_uint2((unsigned int)a.x, (unsigned int)a.y);
1402 }
1403 /** @} */
1404 
1405 /** min */
1406 SUTIL_INLINE SUTIL_HOSTDEVICE uint2 min(const uint2& a, const uint2& b)
1407 {
1408   return make_uint2(min(a.x,b.x), min(a.y,b.y));
1409 }
1410 
1411 /** max */
1412 SUTIL_INLINE SUTIL_HOSTDEVICE uint2 max(const uint2& a, const uint2& b)
1413 {
1414   return make_uint2(max(a.x,b.x), max(a.y,b.y));
1415 }
1416 
1417 /** add
1418 * @{
1419 */
1420 SUTIL_INLINE SUTIL_HOSTDEVICE uint2 operator+(const uint2& a, const uint2& b)
1421 {
1422   return make_uint2(a.x + b.x, a.y + b.y);
1423 }
1424 SUTIL_INLINE SUTIL_HOSTDEVICE void operator+=(uint2& a, const uint2& b)
1425 {
1426   a.x += b.x; a.y += b.y;
1427 }
1428 /** @} */
1429 
1430 /** subtract
1431 * @{
1432 */
1433 SUTIL_INLINE SUTIL_HOSTDEVICE uint2 operator-(const uint2& a, const uint2& b)
1434 {
1435   return make_uint2(a.x - b.x, a.y - b.y);
1436 }
1437 SUTIL_INLINE SUTIL_HOSTDEVICE uint2 operator-(const uint2& a, const unsigned int b)
1438 {
1439   return make_uint2(a.x - b, a.y - b);
1440 }
1441 SUTIL_INLINE SUTIL_HOSTDEVICE void operator-=(uint2& a, const uint2& b)
1442 {
1443   a.x -= b.x; a.y -= b.y;
1444 }
1445 /** @} */
1446 
1447 /** multiply
1448 * @{
1449 */
1450 SUTIL_INLINE SUTIL_HOSTDEVICE uint2 operator*(const uint2& a, const uint2& b)
1451 {
1452   return make_uint2(a.x * b.x, a.y * b.y);
1453 }
1454 SUTIL_INLINE SUTIL_HOSTDEVICE uint2 operator*(const uint2& a, const unsigned int s)
1455 {
1456   return make_uint2(a.x * s, a.y * s);
1457 }
1458 SUTIL_INLINE SUTIL_HOSTDEVICE uint2 operator*(const unsigned int s, const uint2& a)
1459 {
1460   return make_uint2(a.x * s, a.y * s);
1461 }
1462 SUTIL_INLINE SUTIL_HOSTDEVICE void operator*=(uint2& a, const unsigned int s)
1463 {
1464   a.x *= s; a.y *= s;
1465 }
1466 /** @} */
1467 
1468 /** clamp
1469 * @{
1470 */
1471 SUTIL_INLINE SUTIL_HOSTDEVICE uint2 clamp(const uint2& v, const unsigned int a, const unsigned int b)
1472 {
1473   return make_uint2(clamp(v.x, a, b), clamp(v.y, a, b));
1474 }
1475 
1476 SUTIL_INLINE SUTIL_HOSTDEVICE uint2 clamp(const uint2& v, const uint2& a, const uint2& b)
1477 {
1478   return make_uint2(clamp(v.x, a.x, b.x), clamp(v.y, a.y, b.y));
1479 }
1480 /** @} */
1481 
1482 /** equality
1483 * @{
1484 */
1485 SUTIL_INLINE SUTIL_HOSTDEVICE bool operator==(const uint2& a, const uint2& b)
1486 {
1487   return a.x == b.x && a.y == b.y;
1488 }
1489 
1490 SUTIL_INLINE SUTIL_HOSTDEVICE bool operator!=(const uint2& a, const uint2& b)
1491 {
1492   return a.x != b.x || a.y != b.y;
1493 }
1494 /** @} */
1495 
1496 /** If used on the device, this could place the the 'v' in local memory */
1497 SUTIL_INLINE SUTIL_HOSTDEVICE unsigned int getByIndex(const uint2& v, unsigned int i)
1498 {
1499   return ((unsigned int*)(&v))[i];
1500 }
1501 
1502 /** If used on the device, this could place the the 'v' in local memory */
1503 SUTIL_INLINE SUTIL_HOSTDEVICE void setByIndex(uint2& v, int i, unsigned int x)
1504 {
1505   ((unsigned int*)(&v))[i] = x;
1506 }
1507 
1508 
1509 /* uint3 functions */
1510 /******************************************************************************/
1511 
1512 /** additional constructors
1513 * @{
1514 */
1515 SUTIL_INLINE SUTIL_HOSTDEVICE uint3 make_uint3(const unsigned int s)
1516 {
1517   return make_uint3(s, s, s);
1518 }
1519 SUTIL_INLINE SUTIL_HOSTDEVICE uint3 make_uint3(const float3& a)
1520 {
1521   return make_uint3((unsigned int)a.x, (unsigned int)a.y, (unsigned int)a.z);
1522 }
1523 /** @} */
1524 
1525 /** min */
1526 SUTIL_INLINE SUTIL_HOSTDEVICE uint3 min(const uint3& a, const uint3& b)
1527 {
1528   return make_uint3(min(a.x,b.x), min(a.y,b.y), min(a.z,b.z));
1529 }
1530 
1531 /** max */
1532 SUTIL_INLINE SUTIL_HOSTDEVICE uint3 max(const uint3& a, const uint3& b)
1533 {
1534   return make_uint3(max(a.x,b.x), max(a.y,b.y), max(a.z,b.z));
1535 }
1536 
1537 /** add
1538 * @{
1539 */
1540 SUTIL_INLINE SUTIL_HOSTDEVICE uint3 operator+(const uint3& a, const uint3& b)
1541 {
1542   return make_uint3(a.x + b.x, a.y + b.y, a.z + b.z);
1543 }
1544 SUTIL_INLINE SUTIL_HOSTDEVICE void operator+=(uint3& a, const uint3& b)
1545 {
1546   a.x += b.x; a.y += b.y; a.z += b.z;
1547 }
1548 /** @} */
1549 
1550 /** subtract
1551 * @{
1552 */
1553 SUTIL_INLINE SUTIL_HOSTDEVICE uint3 operator-(const uint3& a, const uint3& b)
1554 {
1555   return make_uint3(a.x - b.x, a.y - b.y, a.z - b.z);
1556 }
1557 
1558 SUTIL_INLINE SUTIL_HOSTDEVICE void operator-=(uint3& a, const uint3& b)
1559 {
1560   a.x -= b.x; a.y -= b.y; a.z -= b.z;
1561 }
1562 /** @} */
1563 
1564 /** multiply
1565 * @{
1566 */
1567 SUTIL_INLINE SUTIL_HOSTDEVICE uint3 operator*(const uint3& a, const uint3& b)
1568 {
1569   return make_uint3(a.x * b.x, a.y * b.y, a.z * b.z);
1570 }
1571 SUTIL_INLINE SUTIL_HOSTDEVICE uint3 operator*(const uint3& a, const unsigned int s)
1572 {
1573   return make_uint3(a.x * s, a.y * s, a.z * s);
1574 }
1575 SUTIL_INLINE SUTIL_HOSTDEVICE uint3 operator*(const unsigned int s, const uint3& a)
1576 {
1577   return make_uint3(a.x * s, a.y * s, a.z * s);
1578 }
1579 SUTIL_INLINE SUTIL_HOSTDEVICE void operator*=(uint3& a, const unsigned int s)
1580 {
1581   a.x *= s; a.y *= s; a.z *= s;
1582 }
1583 /** @} */
1584 
1585 /** divide
1586 * @{
1587 */
1588 SUTIL_INLINE SUTIL_HOSTDEVICE uint3 operator/(const uint3& a, const uint3& b)
1589 {
1590   return make_uint3(a.x / b.x, a.y / b.y, a.z / b.z);
1591 }
1592 SUTIL_INLINE SUTIL_HOSTDEVICE uint3 operator/(const uint3& a, const unsigned int s)
1593 {
1594   return make_uint3(a.x / s, a.y / s, a.z / s);
1595 }
1596 SUTIL_INLINE SUTIL_HOSTDEVICE uint3 operator/(const unsigned int s, const uint3& a)
1597 {
1598   return make_uint3(s / a.x, s / a.y, s / a.z);
1599 }
1600 SUTIL_INLINE SUTIL_HOSTDEVICE void operator/=(uint3& a, const unsigned int s)
1601 {
1602   a.x /= s; a.y /= s; a.z /= s;
1603 }
1604 /** @} */
1605 
1606 /** clamp
1607 * @{
1608 */
1609 SUTIL_INLINE SUTIL_HOSTDEVICE uint3 clamp(const uint3& v, const unsigned int a, const unsigned int b)
1610 {
1611   return make_uint3(clamp(v.x, a, b), clamp(v.y, a, b), clamp(v.z, a, b));
1612 }
1613 
1614 SUTIL_INLINE SUTIL_HOSTDEVICE uint3 clamp(const uint3& v, const uint3& a, const uint3& b)
1615 {
1616   return make_uint3(clamp(v.x, a.x, b.x), clamp(v.y, a.y, b.y), clamp(v.z, a.z, b.z));
1617 }
1618 /** @} */
1619 
1620 /** equality
1621 * @{
1622 */
1623 SUTIL_INLINE SUTIL_HOSTDEVICE bool operator==(const uint3& a, const uint3& b)
1624 {
1625   return a.x == b.x && a.y == b.y && a.z == b.z;
1626 }
1627 
1628 SUTIL_INLINE SUTIL_HOSTDEVICE bool operator!=(const uint3& a, const uint3& b)
1629 {
1630   return a.x != b.x || a.y != b.y || a.z != b.z;
1631 }
1632 /** @} */
1633 
1634 /** If used on the device, this could place the the 'v' in local memory
1635 */
1636 SUTIL_INLINE SUTIL_HOSTDEVICE unsigned int getByIndex(const uint3& v, unsigned int i)
1637 {
1638   return ((unsigned int*)(&v))[i];
1639 }
1640 
1641 /** If used on the device, this could place the the 'v' in local memory
1642 */
1643 SUTIL_INLINE SUTIL_HOSTDEVICE void setByIndex(uint3& v, int i, unsigned int x)
1644 {
1645   ((unsigned int*)(&v))[i] = x;
1646 }
1647 
1648 
1649 /* uint4 functions */
1650 /******************************************************************************/
1651 
1652 /** additional constructors
1653 * @{
1654 */
1655 SUTIL_INLINE SUTIL_HOSTDEVICE uint4 make_uint4(const unsigned int s)
1656 {
1657   return make_uint4(s, s, s, s);
1658 }
1659 SUTIL_INLINE SUTIL_HOSTDEVICE uint4 make_uint4(const float4& a)
1660 {
1661   return make_uint4((unsigned int)a.x, (unsigned int)a.y, (unsigned int)a.z, (unsigned int)a.w);
1662 }
1663 /** @} */
1664 
1665 /** min
1666 * @{
1667 */
1668 SUTIL_INLINE SUTIL_HOSTDEVICE uint4 min(const uint4& a, const uint4& b)
1669 {
1670   return make_uint4(min(a.x,b.x), min(a.y,b.y), min(a.z,b.z), min(a.w,b.w));
1671 }
1672 /** @} */
1673 
1674 /** max
1675 * @{
1676 */
1677 SUTIL_INLINE SUTIL_HOSTDEVICE uint4 max(const uint4& a, const uint4& b)
1678 {
1679   return make_uint4(max(a.x,b.x), max(a.y,b.y), max(a.z,b.z), max(a.w,b.w));
1680 }
1681 /** @} */
1682 
1683 /** add
1684 * @{
1685 */
1686 SUTIL_INLINE SUTIL_HOSTDEVICE uint4 operator+(const uint4& a, const uint4& b)
1687 {
1688   return make_uint4(a.x + b.x, a.y + b.y, a.z + b.z, a.w + b.w);
1689 }
1690 SUTIL_INLINE SUTIL_HOSTDEVICE void operator+=(uint4& a, const uint4& b)
1691 {
1692   a.x += b.x; a.y += b.y; a.z += b.z; a.w += b.w;
1693 }
1694 /** @} */
1695 
1696 /** subtract
1697 * @{
1698 */
1699 SUTIL_INLINE SUTIL_HOSTDEVICE uint4 operator-(const uint4& a, const uint4& b)
1700 {
1701   return make_uint4(a.x - b.x, a.y - b.y, a.z - b.z, a.w - b.w);
1702 }
1703 
1704 SUTIL_INLINE SUTIL_HOSTDEVICE void operator-=(uint4& a, const uint4& b)
1705 {
1706   a.x -= b.x; a.y -= b.y; a.z -= b.z; a.w -= b.w;
1707 }
1708 /** @} */
1709 
1710 /** multiply
1711 * @{
1712 */
1713 SUTIL_INLINE SUTIL_HOSTDEVICE uint4 operator*(const uint4& a, const uint4& b)
1714 {
1715   return make_uint4(a.x * b.x, a.y * b.y, a.z * b.z, a.w * b.w);
1716 }
1717 SUTIL_INLINE SUTIL_HOSTDEVICE uint4 operator*(const uint4& a, const unsigned int s)
1718 {
1719   return make_uint4(a.x * s, a.y * s, a.z * s, a.w * s);
1720 }
1721 SUTIL_INLINE SUTIL_HOSTDEVICE uint4 operator*(const unsigned int s, const uint4& a)
1722 {
1723   return make_uint4(a.x * s, a.y * s, a.z * s, a.w * s);
1724 }
1725 SUTIL_INLINE SUTIL_HOSTDEVICE void operator*=(uint4& a, const unsigned int s)
1726 {
1727   a.x *= s; a.y *= s; a.z *= s; a.w *= s;
1728 }
1729 /** @} */
1730 
1731 /** divide
1732 * @{
1733 */
1734 SUTIL_INLINE SUTIL_HOSTDEVICE uint4 operator/(const uint4& a, const uint4& b)
1735 {
1736   return make_uint4(a.x / b.x, a.y / b.y, a.z / b.z, a.w / b.w);
1737 }
1738 SUTIL_INLINE SUTIL_HOSTDEVICE uint4 operator/(const uint4& a, const unsigned int s)
1739 {
1740   return make_uint4(a.x / s, a.y / s, a.z / s, a.w / s);
1741 }
1742 SUTIL_INLINE SUTIL_HOSTDEVICE uint4 operator/(const unsigned int s, const uint4& a)
1743 {
1744   return make_uint4(s / a.x, s / a.y, s / a.z, s / a.w);
1745 }
1746 SUTIL_INLINE SUTIL_HOSTDEVICE void operator/=(uint4& a, const unsigned int s)
1747 {
1748   a.x /= s; a.y /= s; a.z /= s; a.w /= s;
1749 }
1750 /** @} */
1751 
1752 /** clamp
1753 * @{
1754 */
1755 SUTIL_INLINE SUTIL_HOSTDEVICE uint4 clamp(const uint4& v, const unsigned int a, const unsigned int b)
1756 {
1757   return make_uint4(clamp(v.x, a, b), clamp(v.y, a, b), clamp(v.z, a, b), clamp(v.w, a, b));
1758 }
1759 
1760 SUTIL_INLINE SUTIL_HOSTDEVICE uint4 clamp(const uint4& v, const uint4& a, const uint4& b)
1761 {
1762   return make_uint4(clamp(v.x, a.x, b.x), clamp(v.y, a.y, b.y), clamp(v.z, a.z, b.z), clamp(v.w, a.w, b.w));
1763 }
1764 /** @} */
1765 
1766 /** equality
1767 * @{
1768 */
1769 SUTIL_INLINE SUTIL_HOSTDEVICE bool operator==(const uint4& a, const uint4& b)
1770 {
1771   return a.x == b.x && a.y == b.y && a.z == b.z && a.w == b.w;
1772 }
1773 
1774 SUTIL_INLINE SUTIL_HOSTDEVICE bool operator!=(const uint4& a, const uint4& b)
1775 {
1776   return a.x != b.x || a.y != b.y || a.z != b.z || a.w != b.w;
1777 }
1778 /** @} */
1779 
1780 /** If used on the device, this could place the the 'v' in local memory
1781 */
1782 SUTIL_INLINE SUTIL_HOSTDEVICE unsigned int getByIndex(const uint4& v, unsigned int i)
1783 {
1784   return ((unsigned int*)(&v))[i];
1785 }
1786 
1787 /** If used on the device, this could place the the 'v' in local memory
1788 */
1789 SUTIL_INLINE SUTIL_HOSTDEVICE void setByIndex(uint4& v, int i, unsigned int x)
1790 {
1791   ((unsigned int*)(&v))[i] = x;
1792 }
1793 
1794 /* long long functions */
1795 /******************************************************************************/
1796 
1797 /** clamp */
1798 SUTIL_INLINE SUTIL_HOSTDEVICE long long clamp(const long long f, const long long a, const long long b)
1799 {
1800     return max(a, min(f, b));
1801 }
1802 
1803 /** If used on the device, this could place the the 'v' in local memory */
1804 SUTIL_INLINE SUTIL_HOSTDEVICE long long getByIndex(const longlong1& v, int i)
1805 {
1806     return ((long long*)(&v))[i];
1807 }
1808 
1809 /** If used on the device, this could place the the 'v' in local memory */
1810 SUTIL_INLINE SUTIL_HOSTDEVICE void setByIndex(longlong1& v, int i, long long x)
1811 {
1812     ((long long*)(&v))[i] = x;
1813 }
1814 
1815 
1816 /* longlong2 functions */
1817 /******************************************************************************/
1818 
1819 /** additional constructors
1820 * @{
1821 */
1822 SUTIL_INLINE SUTIL_HOSTDEVICE longlong2 make_longlong2(const long long s)
1823 {
1824     return make_longlong2(s, s);
1825 }
1826 SUTIL_INLINE SUTIL_HOSTDEVICE longlong2 make_longlong2(const float2& a)
1827 {
1828     return make_longlong2(int(a.x), int(a.y));
1829 }
1830 /** @} */
1831 
1832 /** negate */
1833 SUTIL_INLINE SUTIL_HOSTDEVICE longlong2 operator-(const longlong2& a)
1834 {
1835     return make_longlong2(-a.x, -a.y);
1836 }
1837 
1838 /** min */
1839 SUTIL_INLINE SUTIL_HOSTDEVICE longlong2 min(const longlong2& a, const longlong2& b)
1840 {
1841     return make_longlong2(min(a.x, b.x), min(a.y, b.y));
1842 }
1843 
1844 /** max */
1845 SUTIL_INLINE SUTIL_HOSTDEVICE longlong2 max(const longlong2& a, const longlong2& b)
1846 {
1847     return make_longlong2(max(a.x, b.x), max(a.y, b.y));
1848 }
1849 
1850 /** add
1851 * @{
1852 */
1853 SUTIL_INLINE SUTIL_HOSTDEVICE longlong2 operator+(const longlong2& a, const longlong2& b)
1854 {
1855     return make_longlong2(a.x + b.x, a.y + b.y);
1856 }
1857 SUTIL_INLINE SUTIL_HOSTDEVICE void operator+=(longlong2& a, const longlong2& b)
1858 {
1859     a.x += b.x; a.y += b.y;
1860 }
1861 /** @} */
1862 
1863 /** subtract
1864 * @{
1865 */
1866 SUTIL_INLINE SUTIL_HOSTDEVICE longlong2 operator-(const longlong2& a, const longlong2& b)
1867 {
1868     return make_longlong2(a.x - b.x, a.y - b.y);
1869 }
1870 SUTIL_INLINE SUTIL_HOSTDEVICE longlong2 operator-(const longlong2& a, const long long b)
1871 {
1872     return make_longlong2(a.x - b, a.y - b);
1873 }
1874 SUTIL_INLINE SUTIL_HOSTDEVICE void operator-=(longlong2& a, const longlong2& b)
1875 {
1876     a.x -= b.x; a.y -= b.y;
1877 }
1878 /** @} */
1879 
1880 /** multiply
1881 * @{
1882 */
1883 SUTIL_INLINE SUTIL_HOSTDEVICE longlong2 operator*(const longlong2& a, const longlong2& b)
1884 {
1885     return make_longlong2(a.x * b.x, a.y * b.y);
1886 }
1887 SUTIL_INLINE SUTIL_HOSTDEVICE longlong2 operator*(const longlong2& a, const long long s)
1888 {
1889     return make_longlong2(a.x * s, a.y * s);
1890 }
1891 SUTIL_INLINE SUTIL_HOSTDEVICE longlong2 operator*(const long long s, const longlong2& a)
1892 {
1893     return make_longlong2(a.x * s, a.y * s);
1894 }
1895 SUTIL_INLINE SUTIL_HOSTDEVICE void operator*=(longlong2& a, const long long s)
1896 {
1897     a.x *= s; a.y *= s;
1898 }
1899 /** @} */
1900 
1901 /** clamp
1902 * @{
1903 */
1904 SUTIL_INLINE SUTIL_HOSTDEVICE longlong2 clamp(const longlong2& v, const long long a, const long long b)
1905 {
1906     return make_longlong2(clamp(v.x, a, b), clamp(v.y, a, b));
1907 }
1908 
1909 SUTIL_INLINE SUTIL_HOSTDEVICE longlong2 clamp(const longlong2& v, const longlong2& a, const longlong2& b)
1910 {
1911     return make_longlong2(clamp(v.x, a.x, b.x), clamp(v.y, a.y, b.y));
1912 }
1913 /** @} */
1914 
1915 /** equality
1916 * @{
1917 */
1918 SUTIL_INLINE SUTIL_HOSTDEVICE bool operator==(const longlong2& a, const longlong2& b)
1919 {
1920     return a.x == b.x && a.y == b.y;
1921 }
1922 
1923 SUTIL_INLINE SUTIL_HOSTDEVICE bool operator!=(const longlong2& a, const longlong2& b)
1924 {
1925     return a.x != b.x || a.y != b.y;
1926 }
1927 /** @} */
1928 
1929 /** If used on the device, this could place the the 'v' in local memory */
1930 SUTIL_INLINE SUTIL_HOSTDEVICE long long getByIndex(const longlong2& v, int i)
1931 {
1932     return ((long long*)(&v))[i];
1933 }
1934 
1935 /** If used on the device, this could place the the 'v' in local memory */
1936 SUTIL_INLINE SUTIL_HOSTDEVICE void setByIndex(longlong2& v, int i, long long x)
1937 {
1938     ((long long*)(&v))[i] = x;
1939 }
1940 
1941 
1942 /* longlong3 functions */
1943 /******************************************************************************/
1944 
1945 /** additional constructors
1946 * @{
1947 */
1948 SUTIL_INLINE SUTIL_HOSTDEVICE longlong3 make_longlong3(const long long s)
1949 {
1950     return make_longlong3(s, s, s);
1951 }
1952 SUTIL_INLINE SUTIL_HOSTDEVICE longlong3 make_longlong3(const float3& a)
1953 {
1954     return make_longlong3( (long long)a.x, (long long)a.y, (long long)a.z);
1955 }
1956 /** @} */
1957 
1958 /** negate */
1959 SUTIL_INLINE SUTIL_HOSTDEVICE longlong3 operator-(const longlong3& a)
1960 {
1961     return make_longlong3(-a.x, -a.y, -a.z);
1962 }
1963 
1964 /** min */
1965 SUTIL_INLINE SUTIL_HOSTDEVICE longlong3 min(const longlong3& a, const longlong3& b)
1966 {
1967     return make_longlong3(min(a.x, b.x), min(a.y, b.y), min(a.z, b.z));
1968 }
1969 
1970 /** max */
1971 SUTIL_INLINE SUTIL_HOSTDEVICE longlong3 max(const longlong3& a, const longlong3& b)
1972 {
1973     return make_longlong3(max(a.x, b.x), max(a.y, b.y), max(a.z, b.z));
1974 }
1975 
1976 /** add
1977 * @{
1978 */
1979 SUTIL_INLINE SUTIL_HOSTDEVICE longlong3 operator+(const longlong3& a, const longlong3& b)
1980 {
1981     return make_longlong3(a.x + b.x, a.y + b.y, a.z + b.z);
1982 }
1983 SUTIL_INLINE SUTIL_HOSTDEVICE void operator+=(longlong3& a, const longlong3& b)
1984 {
1985     a.x += b.x; a.y += b.y; a.z += b.z;
1986 }
1987 /** @} */
1988 
1989 /** subtract
1990 * @{
1991 */
1992 SUTIL_INLINE SUTIL_HOSTDEVICE longlong3 operator-(const longlong3& a, const longlong3& b)
1993 {
1994     return make_longlong3(a.x - b.x, a.y - b.y, a.z - b.z);
1995 }
1996 
1997 SUTIL_INLINE SUTIL_HOSTDEVICE void operator-=(longlong3& a, const longlong3& b)
1998 {
1999     a.x -= b.x; a.y -= b.y; a.z -= b.z;
2000 }
2001 /** @} */
2002 
2003 /** multiply
2004 * @{
2005 */
2006 SUTIL_INLINE SUTIL_HOSTDEVICE longlong3 operator*(const longlong3& a, const longlong3& b)
2007 {
2008     return make_longlong3(a.x * b.x, a.y * b.y, a.z * b.z);
2009 }
2010 SUTIL_INLINE SUTIL_HOSTDEVICE longlong3 operator*(const longlong3& a, const long long s)
2011 {
2012     return make_longlong3(a.x * s, a.y * s, a.z * s);
2013 }
2014 SUTIL_INLINE SUTIL_HOSTDEVICE longlong3 operator*(const long long s, const longlong3& a)
2015 {
2016     return make_longlong3(a.x * s, a.y * s, a.z * s);
2017 }
2018 SUTIL_INLINE SUTIL_HOSTDEVICE void operator*=(longlong3& a, const long long s)
2019 {
2020     a.x *= s; a.y *= s; a.z *= s;
2021 }
2022 /** @} */
2023 
2024 /** divide
2025 * @{
2026 */
2027 SUTIL_INLINE SUTIL_HOSTDEVICE longlong3 operator/(const longlong3& a, const longlong3& b)
2028 {
2029     return make_longlong3(a.x / b.x, a.y / b.y, a.z / b.z);
2030 }
2031 SUTIL_INLINE SUTIL_HOSTDEVICE longlong3 operator/(const longlong3& a, const long long s)
2032 {
2033     return make_longlong3(a.x / s, a.y / s, a.z / s);
2034 }
2035 SUTIL_INLINE SUTIL_HOSTDEVICE longlong3 operator/(const long long s, const longlong3& a)
2036 {
2037     return make_longlong3(s /a.x, s / a.y, s / a.z);
2038 }
2039 SUTIL_INLINE SUTIL_HOSTDEVICE void operator/=(longlong3& a, const long long s)
2040 {
2041     a.x /= s; a.y /= s; a.z /= s;
2042 }
2043 /** @} */
2044 
2045 /** clamp
2046 * @{
2047 */
2048 SUTIL_INLINE SUTIL_HOSTDEVICE longlong3 clamp(const longlong3& v, const long long a, const long long b)
2049 {
2050     return make_longlong3(clamp(v.x, a, b), clamp(v.y, a, b), clamp(v.z, a, b));
2051 }
2052 
2053 SUTIL_INLINE SUTIL_HOSTDEVICE longlong3 clamp(const longlong3& v, const longlong3& a, const longlong3& b)
2054 {
2055     return make_longlong3(clamp(v.x, a.x, b.x), clamp(v.y, a.y, b.y), clamp(v.z, a.z, b.z));
2056 }
2057 /** @} */
2058 
2059 /** equality
2060 * @{
2061 */
2062 SUTIL_INLINE SUTIL_HOSTDEVICE bool operator==(const longlong3& a, const longlong3& b)
2063 {
2064     return a.x == b.x && a.y == b.y && a.z == b.z;
2065 }
2066 
2067 SUTIL_INLINE SUTIL_HOSTDEVICE bool operator!=(const longlong3& a, const longlong3& b)
2068 {
2069     return a.x != b.x || a.y != b.y || a.z != b.z;
2070 }
2071 /** @} */
2072 
2073 /** If used on the device, this could place the the 'v' in local memory */
2074 SUTIL_INLINE SUTIL_HOSTDEVICE long long getByIndex(const longlong3& v, int i)
2075 {
2076     return ((long long*)(&v))[i];
2077 }
2078 
2079 /** If used on the device, this could place the the 'v' in local memory */
2080 SUTIL_INLINE SUTIL_HOSTDEVICE void setByIndex(longlong3& v, int i, int x)
2081 {
2082     ((long long*)(&v))[i] = x;
2083 }
2084 
2085 
2086 /* LONGLONG4 functions */
2087 /******************************************************************************/
2088 
2089 /** additional constructors
2090 * @{
2091 */
2092 SUTIL_INLINE SUTIL_HOSTDEVICE LONGLONG4 MAKE_LONGLONG4(const long long s)
2093 {
2094     return MAKE_LONGLONG4(s, s, s, s);
2095 }
2096 SUTIL_INLINE SUTIL_HOSTDEVICE LONGLONG4 MAKE_LONGLONG4(const float4& a)
2097 {
2098     return MAKE_LONGLONG4((long long)a.x, (long long)a.y, (long long)a.z, (long long)a.w);
2099 }
2100 /** @} */
2101 
2102 /** negate */
2103 SUTIL_INLINE SUTIL_HOSTDEVICE LONGLONG4 operator-(const LONGLONG4& a)
2104 {
2105     return MAKE_LONGLONG4(-a.x, -a.y, -a.z, -a.w);
2106 }
2107 
2108 /** min */
2109 SUTIL_INLINE SUTIL_HOSTDEVICE LONGLONG4 min(const LONGLONG4& a, const LONGLONG4& b)
2110 {
2111     return MAKE_LONGLONG4(min(a.x, b.x), min(a.y, b.y), min(a.z, b.z), min(a.w, b.w));
2112 }
2113 
2114 /** max */
2115 SUTIL_INLINE SUTIL_HOSTDEVICE LONGLONG4 max(const LONGLONG4& a, const LONGLONG4& b)
2116 {
2117     return MAKE_LONGLONG4(max(a.x, b.x), max(a.y, b.y), max(a.z, b.z), max(a.w, b.w));
2118 }
2119 
2120 /** add
2121 * @{
2122 */
2123 SUTIL_INLINE SUTIL_HOSTDEVICE LONGLONG4 operator+(const LONGLONG4& a, const LONGLONG4& b)
2124 {
2125     return MAKE_LONGLONG4(a.x + b.x, a.y + b.y, a.z + b.z, a.w + b.w);
2126 }
2127 SUTIL_INLINE SUTIL_HOSTDEVICE void operator+=(LONGLONG4& a, const LONGLONG4& b)
2128 {
2129     a.x += b.x; a.y += b.y; a.z += b.z; a.w += b.w;
2130 }
2131 /** @} */
2132 
2133 /** subtract
2134 * @{
2135 */
2136 SUTIL_INLINE SUTIL_HOSTDEVICE LONGLONG4 operator-(const LONGLONG4& a, const LONGLONG4& b)
2137 {
2138     return MAKE_LONGLONG4(a.x - b.x, a.y - b.y, a.z - b.z, a.w - b.w);
2139 }
2140 
2141 SUTIL_INLINE SUTIL_HOSTDEVICE void operator-=(LONGLONG4& a, const LONGLONG4& b)
2142 {
2143     a.x -= b.x; a.y -= b.y; a.z -= b.z; a.w -= b.w;
2144 }
2145 /** @} */
2146 
2147 /** multiply
2148 * @{
2149 */
2150 SUTIL_INLINE SUTIL_HOSTDEVICE LONGLONG4 operator*(const LONGLONG4& a, const LONGLONG4& b)
2151 {
2152     return MAKE_LONGLONG4(a.x * b.x, a.y * b.y, a.z * b.z, a.w * b.w);
2153 }
2154 SUTIL_INLINE SUTIL_HOSTDEVICE LONGLONG4 operator*(const LONGLONG4& a, const long long s)
2155 {
2156     return MAKE_LONGLONG4(a.x * s, a.y * s, a.z * s, a.w * s);
2157 }
2158 SUTIL_INLINE SUTIL_HOSTDEVICE LONGLONG4 operator*(const long long s, const LONGLONG4& a)
2159 {
2160     return MAKE_LONGLONG4(a.x * s, a.y * s, a.z * s, a.w * s);
2161 }
2162 SUTIL_INLINE SUTIL_HOSTDEVICE void operator*=(LONGLONG4& a, const long long s)
2163 {
2164     a.x *= s; a.y *= s; a.z *= s; a.w *= s;
2165 }
2166 /** @} */
2167 
2168 /** divide
2169 * @{
2170 */
2171 SUTIL_INLINE SUTIL_HOSTDEVICE LONGLONG4 operator/(const LONGLONG4& a, const LONGLONG4& b)
2172 {
2173     return MAKE_LONGLONG4(a.x / b.x, a.y / b.y, a.z / b.z, a.w / b.w);
2174 }
2175 SUTIL_INLINE SUTIL_HOSTDEVICE LONGLONG4 operator/(const LONGLONG4& a, const long long s)
2176 {
2177     return MAKE_LONGLONG4(a.x / s, a.y / s, a.z / s, a.w / s);
2178 }
2179 SUTIL_INLINE SUTIL_HOSTDEVICE LONGLONG4 operator/(const long long s, const LONGLONG4& a)
2180 {
2181     return MAKE_LONGLONG4(s / a.x, s / a.y, s / a.z, s / a.w);
2182 }
2183 SUTIL_INLINE SUTIL_HOSTDEVICE void operator/=(LONGLONG4& a, const long long s)
2184 {
2185     a.x /= s; a.y /= s; a.z /= s; a.w /= s;
2186 }
2187 /** @} */
2188 
2189 /** clamp
2190 * @{
2191 */
2192 SUTIL_INLINE SUTIL_HOSTDEVICE LONGLONG4 clamp(const LONGLONG4& v, const long long a, const long long b)
2193 {
2194     return MAKE_LONGLONG4(clamp(v.x, a, b), clamp(v.y, a, b), clamp(v.z, a, b), clamp(v.w, a, b));
2195 }
2196 
2197 SUTIL_INLINE SUTIL_HOSTDEVICE LONGLONG4 clamp(const LONGLONG4& v, const LONGLONG4& a, const LONGLONG4& b)
2198 {
2199     return MAKE_LONGLONG4(clamp(v.x, a.x, b.x), clamp(v.y, a.y, b.y), clamp(v.z, a.z, b.z), clamp(v.w, a.w, b.w));
2200 }
2201 /** @} */
2202 
2203 /** equality
2204 * @{
2205 */
2206 SUTIL_INLINE SUTIL_HOSTDEVICE bool operator==(const LONGLONG4& a, const LONGLONG4& b)
2207 {
2208     return a.x == b.x && a.y == b.y && a.z == b.z && a.w == b.w;
2209 }
2210 
2211 SUTIL_INLINE SUTIL_HOSTDEVICE bool operator!=(const LONGLONG4& a, const LONGLONG4& b)
2212 {
2213     return a.x != b.x || a.y != b.y || a.z != b.z || a.w != b.w;
2214 }
2215 /** @} */
2216 
2217 /** If used on the device, this could place the the 'v' in local memory */
2218 SUTIL_INLINE SUTIL_HOSTDEVICE long long getByIndex(const LONGLONG4& v, int i)
2219 {
2220     return ((long long*)(&v))[i];
2221 }
2222 
2223 /** If used on the device, this could place the the 'v' in local memory */
2224 SUTIL_INLINE SUTIL_HOSTDEVICE void setByIndex(LONGLONG4& v, int i, long long x)
2225 {
2226     ((long long*)(&v))[i] = x;
2227 }
2228 
2229 /* ulonglong functions */
2230 /******************************************************************************/
2231 
2232 /** clamp */
2233 SUTIL_INLINE SUTIL_HOSTDEVICE unsigned long long clamp(const unsigned long long f, const unsigned long long a, const unsigned long long b)
2234 {
2235     return max(a, min(f, b));
2236 }
2237 
2238 /** If used on the device, this could place the the 'v' in local memory */
2239 SUTIL_INLINE SUTIL_HOSTDEVICE unsigned long long getByIndex(const ulonglong1& v, unsigned int i)
2240 {
2241     return ((unsigned long long*)(&v))[i];
2242 }
2243 
2244 /** If used on the device, this could place the the 'v' in local memory */
2245 SUTIL_INLINE SUTIL_HOSTDEVICE void setByIndex(ulonglong1& v, int i, unsigned long long x)
2246 {
2247     ((unsigned long long*)(&v))[i] = x;
2248 }
2249 
2250 
2251 /* ulonglong2 functions */
2252 /******************************************************************************/
2253 
2254 /** additional constructors
2255 * @{
2256 */
2257 SUTIL_INLINE SUTIL_HOSTDEVICE ulonglong2 make_ulonglong2(const unsigned long long s)
2258 {
2259     return make_ulonglong2(s, s);
2260 }
2261 SUTIL_INLINE SUTIL_HOSTDEVICE ulonglong2 make_ulonglong2(const float2& a)
2262 {
2263     return make_ulonglong2((unsigned long long)a.x, (unsigned long long)a.y);
2264 }
2265 /** @} */
2266 
2267 /** min */
2268 SUTIL_INLINE SUTIL_HOSTDEVICE ulonglong2 min(const ulonglong2& a, const ulonglong2& b)
2269 {
2270     return make_ulonglong2(min(a.x, b.x), min(a.y, b.y));
2271 }
2272 
2273 /** max */
2274 SUTIL_INLINE SUTIL_HOSTDEVICE ulonglong2 max(const ulonglong2& a, const ulonglong2& b)
2275 {
2276     return make_ulonglong2(max(a.x, b.x), max(a.y, b.y));
2277 }
2278 
2279 /** add
2280 * @{
2281 */
2282 SUTIL_INLINE SUTIL_HOSTDEVICE ulonglong2 operator+(const ulonglong2& a, const ulonglong2& b)
2283 {
2284     return make_ulonglong2(a.x + b.x, a.y + b.y);
2285 }
2286 SUTIL_INLINE SUTIL_HOSTDEVICE void operator+=(ulonglong2& a, const ulonglong2& b)
2287 {
2288     a.x += b.x; a.y += b.y;
2289 }
2290 /** @} */
2291 
2292 /** subtract
2293 * @{
2294 */
2295 SUTIL_INLINE SUTIL_HOSTDEVICE ulonglong2 operator-(const ulonglong2& a, const ulonglong2& b)
2296 {
2297     return make_ulonglong2(a.x - b.x, a.y - b.y);
2298 }
2299 SUTIL_INLINE SUTIL_HOSTDEVICE ulonglong2 operator-(const ulonglong2& a, const unsigned long long b)
2300 {
2301     return make_ulonglong2(a.x - b, a.y - b);
2302 }
2303 SUTIL_INLINE SUTIL_HOSTDEVICE void operator-=(ulonglong2& a, const ulonglong2& b)
2304 {
2305     a.x -= b.x; a.y -= b.y;
2306 }
2307 /** @} */
2308 
2309 /** multiply
2310 * @{
2311 */
2312 SUTIL_INLINE SUTIL_HOSTDEVICE ulonglong2 operator*(const ulonglong2& a, const ulonglong2& b)
2313 {
2314     return make_ulonglong2(a.x * b.x, a.y * b.y);
2315 }
2316 SUTIL_INLINE SUTIL_HOSTDEVICE ulonglong2 operator*(const ulonglong2& a, const unsigned long long s)
2317 {
2318     return make_ulonglong2(a.x * s, a.y * s);
2319 }
2320 SUTIL_INLINE SUTIL_HOSTDEVICE ulonglong2 operator*(const unsigned long long s, const ulonglong2& a)
2321 {
2322     return make_ulonglong2(a.x * s, a.y * s);
2323 }
2324 SUTIL_INLINE SUTIL_HOSTDEVICE void operator*=(ulonglong2& a, const unsigned long long s)
2325 {
2326     a.x *= s; a.y *= s;
2327 }
2328 /** @} */
2329 
2330 /** clamp
2331 * @{
2332 */
2333 SUTIL_INLINE SUTIL_HOSTDEVICE ulonglong2 clamp(const ulonglong2& v, const unsigned long long a, const unsigned long long b)
2334 {
2335     return make_ulonglong2(clamp(v.x, a, b), clamp(v.y, a, b));
2336 }
2337 
2338 SUTIL_INLINE SUTIL_HOSTDEVICE ulonglong2 clamp(const ulonglong2& v, const ulonglong2& a, const ulonglong2& b)
2339 {
2340     return make_ulonglong2(clamp(v.x, a.x, b.x), clamp(v.y, a.y, b.y));
2341 }
2342 /** @} */
2343 
2344 /** equality
2345 * @{
2346 */
2347 SUTIL_INLINE SUTIL_HOSTDEVICE bool operator==(const ulonglong2& a, const ulonglong2& b)
2348 {
2349     return a.x == b.x && a.y == b.y;
2350 }
2351 
2352 SUTIL_INLINE SUTIL_HOSTDEVICE bool operator!=(const ulonglong2& a, const ulonglong2& b)
2353 {
2354     return a.x != b.x || a.y != b.y;
2355 }
2356 /** @} */
2357 
2358 /** If used on the device, this could place the the 'v' in local memory */
2359 SUTIL_INLINE SUTIL_HOSTDEVICE unsigned long long getByIndex(const ulonglong2& v, unsigned int i)
2360 {
2361     return ((unsigned long long*)(&v))[i];
2362 }
2363 
2364 /** If used on the device, this could place the the 'v' in local memory */
2365 SUTIL_INLINE SUTIL_HOSTDEVICE void setByIndex(ulonglong2& v, int i, unsigned long long x)
2366 {
2367     ((unsigned long long*)(&v))[i] = x;
2368 }
2369 
2370 
2371 /* ulonglong3 functions */
2372 /******************************************************************************/
2373 
2374 /** additional constructors
2375 * @{
2376 */
2377 SUTIL_INLINE SUTIL_HOSTDEVICE ulonglong3 make_ulonglong3(const unsigned long long s)
2378 {
2379     return make_ulonglong3(s, s, s);
2380 }
2381 SUTIL_INLINE SUTIL_HOSTDEVICE ulonglong3 make_ulonglong3(const float3& a)
2382 {
2383     return make_ulonglong3((unsigned long long)a.x, (unsigned long long)a.y, (unsigned long long)a.z);
2384 }
2385 /** @} */
2386 
2387 /** min */
2388 SUTIL_INLINE SUTIL_HOSTDEVICE ulonglong3 min(const ulonglong3& a, const ulonglong3& b)
2389 {
2390     return make_ulonglong3(min(a.x, b.x), min(a.y, b.y), min(a.z, b.z));
2391 }
2392 
2393 /** max */
2394 SUTIL_INLINE SUTIL_HOSTDEVICE ulonglong3 max(const ulonglong3& a, const ulonglong3& b)
2395 {
2396     return make_ulonglong3(max(a.x, b.x), max(a.y, b.y), max(a.z, b.z));
2397 }
2398 
2399 /** add
2400 * @{
2401 */
2402 SUTIL_INLINE SUTIL_HOSTDEVICE ulonglong3 operator+(const ulonglong3& a, const ulonglong3& b)
2403 {
2404     return make_ulonglong3(a.x + b.x, a.y + b.y, a.z + b.z);
2405 }
2406 SUTIL_INLINE SUTIL_HOSTDEVICE void operator+=(ulonglong3& a, const ulonglong3& b)
2407 {
2408     a.x += b.x; a.y += b.y; a.z += b.z;
2409 }
2410 /** @} */
2411 
2412 /** subtract
2413 * @{
2414 */
2415 SUTIL_INLINE SUTIL_HOSTDEVICE ulonglong3 operator-(const ulonglong3& a, const ulonglong3& b)
2416 {
2417     return make_ulonglong3(a.x - b.x, a.y - b.y, a.z - b.z);
2418 }
2419 
2420 SUTIL_INLINE SUTIL_HOSTDEVICE void operator-=(ulonglong3& a, const ulonglong3& b)
2421 {
2422     a.x -= b.x; a.y -= b.y; a.z -= b.z;
2423 }
2424 /** @} */
2425 
2426 /** multiply
2427 * @{
2428 */
2429 SUTIL_INLINE SUTIL_HOSTDEVICE ulonglong3 operator*(const ulonglong3& a, const ulonglong3& b)
2430 {
2431     return make_ulonglong3(a.x * b.x, a.y * b.y, a.z * b.z);
2432 }
2433 SUTIL_INLINE SUTIL_HOSTDEVICE ulonglong3 operator*(const ulonglong3& a, const unsigned long long s)
2434 {
2435     return make_ulonglong3(a.x * s, a.y * s, a.z * s);
2436 }
2437 SUTIL_INLINE SUTIL_HOSTDEVICE ulonglong3 operator*(const unsigned long long s, const ulonglong3& a)
2438 {
2439     return make_ulonglong3(a.x * s, a.y * s, a.z * s);
2440 }
2441 SUTIL_INLINE SUTIL_HOSTDEVICE void operator*=(ulonglong3& a, const unsigned long long s)
2442 {
2443     a.x *= s; a.y *= s; a.z *= s;
2444 }
2445 /** @} */
2446 
2447 /** divide
2448 * @{
2449 */
2450 SUTIL_INLINE SUTIL_HOSTDEVICE ulonglong3 operator/(const ulonglong3& a, const ulonglong3& b)
2451 {
2452     return make_ulonglong3(a.x / b.x, a.y / b.y, a.z / b.z);
2453 }
2454 SUTIL_INLINE SUTIL_HOSTDEVICE ulonglong3 operator/(const ulonglong3& a, const unsigned long long s)
2455 {
2456     return make_ulonglong3(a.x / s, a.y / s, a.z / s);
2457 }
2458 SUTIL_INLINE SUTIL_HOSTDEVICE ulonglong3 operator/(const unsigned long long s, const ulonglong3& a)
2459 {
2460     return make_ulonglong3(s / a.x, s / a.y, s / a.z);
2461 }
2462 SUTIL_INLINE SUTIL_HOSTDEVICE void operator/=(ulonglong3& a, const unsigned long long s)
2463 {
2464     a.x /= s; a.y /= s; a.z /= s;
2465 }
2466 /** @} */
2467 
2468 /** clamp
2469 * @{
2470 */
2471 SUTIL_INLINE SUTIL_HOSTDEVICE ulonglong3 clamp(const ulonglong3& v, const unsigned long long a, const unsigned long long b)
2472 {
2473     return make_ulonglong3(clamp(v.x, a, b), clamp(v.y, a, b), clamp(v.z, a, b));
2474 }
2475 
2476 SUTIL_INLINE SUTIL_HOSTDEVICE ulonglong3 clamp(const ulonglong3& v, const ulonglong3& a, const ulonglong3& b)
2477 {
2478     return make_ulonglong3(clamp(v.x, a.x, b.x), clamp(v.y, a.y, b.y), clamp(v.z, a.z, b.z));
2479 }
2480 /** @} */
2481 
2482 /** equality
2483 * @{
2484 */
2485 SUTIL_INLINE SUTIL_HOSTDEVICE bool operator==(const ulonglong3& a, const ulonglong3& b)
2486 {
2487     return a.x == b.x && a.y == b.y && a.z == b.z;
2488 }
2489 
2490 SUTIL_INLINE SUTIL_HOSTDEVICE bool operator!=(const ulonglong3& a, const ulonglong3& b)
2491 {
2492     return a.x != b.x || a.y != b.y || a.z != b.z;
2493 }
2494 /** @} */
2495 
2496 /** If used on the device, this could place the the 'v' in local memory
2497 */
2498 SUTIL_INLINE SUTIL_HOSTDEVICE unsigned long long getByIndex(const ulonglong3& v, unsigned int i)
2499 {
2500     return ((unsigned long long*)(&v))[i];
2501 }
2502 
2503 /** If used on the device, this could place the the 'v' in local memory
2504 */
2505 SUTIL_INLINE SUTIL_HOSTDEVICE void setByIndex(ulonglong3& v, int i, unsigned long long x)
2506 {
2507     ((unsigned long long*)(&v))[i] = x;
2508 }
2509 
2510 
2511 /* ULONGLONG4 functions */
2512 /******************************************************************************/
2513 
2514 /** additional constructors
2515 * @{
2516 */
2517 SUTIL_INLINE SUTIL_HOSTDEVICE ULONGLONG4 MAKE_ULONGLONG4(const unsigned long long s)
2518 {
2519     return MAKE_ULONGLONG4(s, s, s, s);
2520 }
2521 SUTIL_INLINE SUTIL_HOSTDEVICE ULONGLONG4 MAKE_ULONGLONG4(const float4& a)
2522 {
2523     return MAKE_ULONGLONG4((unsigned long long)a.x, (unsigned long long)a.y, (unsigned long long)a.z, (unsigned long long)a.w);
2524 }
2525 /** @} */
2526 
2527 /** min
2528 * @{
2529 */
2530 SUTIL_INLINE SUTIL_HOSTDEVICE ULONGLONG4 min(const ULONGLONG4& a, const ULONGLONG4& b)
2531 {
2532     return MAKE_ULONGLONG4(min(a.x, b.x), min(a.y, b.y), min(a.z, b.z), min(a.w, b.w));
2533 }
2534 /** @} */
2535 
2536 /** max
2537 * @{
2538 */
2539 SUTIL_INLINE SUTIL_HOSTDEVICE ULONGLONG4 max(const ULONGLONG4& a, const ULONGLONG4& b)
2540 {
2541     return MAKE_ULONGLONG4(max(a.x, b.x), max(a.y, b.y), max(a.z, b.z), max(a.w, b.w));
2542 }
2543 /** @} */
2544 
2545 /** add
2546 * @{
2547 */
2548 SUTIL_INLINE SUTIL_HOSTDEVICE ULONGLONG4 operator+(const ULONGLONG4& a, const ULONGLONG4& b)
2549 {
2550     return MAKE_ULONGLONG4(a.x + b.x, a.y + b.y, a.z + b.z, a.w + b.w);
2551 }
2552 SUTIL_INLINE SUTIL_HOSTDEVICE void operator+=(ULONGLONG4& a, const ULONGLONG4& b)
2553 {
2554     a.x += b.x; a.y += b.y; a.z += b.z; a.w += b.w;
2555 }
2556 /** @} */
2557 
2558 /** subtract
2559 * @{
2560 */
2561 SUTIL_INLINE SUTIL_HOSTDEVICE ULONGLONG4 operator-(const ULONGLONG4& a, const ULONGLONG4& b)
2562 {
2563     return MAKE_ULONGLONG4(a.x - b.x, a.y - b.y, a.z - b.z, a.w - b.w);
2564 }
2565 
2566 SUTIL_INLINE SUTIL_HOSTDEVICE void operator-=(ULONGLONG4& a, const ULONGLONG4& b)
2567 {
2568     a.x -= b.x; a.y -= b.y; a.z -= b.z; a.w -= b.w;
2569 }
2570 /** @} */
2571 
2572 /** multiply
2573 * @{
2574 */
2575 SUTIL_INLINE SUTIL_HOSTDEVICE ULONGLONG4 operator*(const ULONGLONG4& a, const ULONGLONG4& b)
2576 {
2577     return MAKE_ULONGLONG4(a.x * b.x, a.y * b.y, a.z * b.z, a.w * b.w);
2578 }
2579 SUTIL_INLINE SUTIL_HOSTDEVICE ULONGLONG4 operator*(const ULONGLONG4& a, const unsigned long long s)
2580 {
2581     return MAKE_ULONGLONG4(a.x * s, a.y * s, a.z * s, a.w * s);
2582 }
2583 SUTIL_INLINE SUTIL_HOSTDEVICE ULONGLONG4 operator*(const unsigned long long s, const ULONGLONG4& a)
2584 {
2585     return MAKE_ULONGLONG4(a.x * s, a.y * s, a.z * s, a.w * s);
2586 }
2587 SUTIL_INLINE SUTIL_HOSTDEVICE void operator*=(ULONGLONG4& a, const unsigned long long s)
2588 {
2589     a.x *= s; a.y *= s; a.z *= s; a.w *= s;
2590 }
2591 /** @} */
2592 
2593 /** divide
2594 * @{
2595 */
2596 SUTIL_INLINE SUTIL_HOSTDEVICE ULONGLONG4 operator/(const ULONGLONG4& a, const ULONGLONG4& b)
2597 {
2598     return MAKE_ULONGLONG4(a.x / b.x, a.y / b.y, a.z / b.z, a.w / b.w);
2599 }
2600 SUTIL_INLINE SUTIL_HOSTDEVICE ULONGLONG4 operator/(const ULONGLONG4& a, const unsigned long long s)
2601 {
2602     return MAKE_ULONGLONG4(a.x / s, a.y / s, a.z / s, a.w / s);
2603 }
2604 SUTIL_INLINE SUTIL_HOSTDEVICE ULONGLONG4 operator/(const unsigned long long s, const ULONGLONG4& a)
2605 {
2606     return MAKE_ULONGLONG4(s / a.x, s / a.y, s / a.z, s / a.w);
2607 }
2608 SUTIL_INLINE SUTIL_HOSTDEVICE void operator/=(ULONGLONG4& a, const unsigned long long s)
2609 {
2610     a.x /= s; a.y /= s; a.z /= s; a.w /= s;
2611 }
2612 /** @} */
2613 
2614 /** clamp
2615 * @{
2616 */
2617 SUTIL_INLINE SUTIL_HOSTDEVICE ULONGLONG4 clamp(const ULONGLONG4& v, const unsigned long long a, const unsigned long long b)
2618 {
2619     return MAKE_ULONGLONG4(clamp(v.x, a, b), clamp(v.y, a, b), clamp(v.z, a, b), clamp(v.w, a, b));
2620 }
2621 
2622 SUTIL_INLINE SUTIL_HOSTDEVICE ULONGLONG4 clamp(const ULONGLONG4& v, const ULONGLONG4& a, const ULONGLONG4& b)
2623 {
2624     return MAKE_ULONGLONG4(clamp(v.x, a.x, b.x), clamp(v.y, a.y, b.y), clamp(v.z, a.z, b.z), clamp(v.w, a.w, b.w));
2625 }
2626 /** @} */
2627 
2628 /** equality
2629 * @{
2630 */
2631 SUTIL_INLINE SUTIL_HOSTDEVICE bool operator==(const ULONGLONG4& a, const ULONGLONG4& b)
2632 {
2633     return a.x == b.x && a.y == b.y && a.z == b.z && a.w == b.w;
2634 }
2635 
2636 SUTIL_INLINE SUTIL_HOSTDEVICE bool operator!=(const ULONGLONG4& a, const ULONGLONG4& b)
2637 {
2638     return a.x != b.x || a.y != b.y || a.z != b.z || a.w != b.w;
2639 }
2640 /** @} */
2641 
2642 /** If used on the device, this could place the the 'v' in local memory
2643 */
2644 SUTIL_INLINE SUTIL_HOSTDEVICE unsigned long long getByIndex(const ULONGLONG4& v, unsigned int i)
2645 {
2646     return ((unsigned long long*)(&v))[i];
2647 }
2648 
2649 /** If used on the device, this could place the the 'v' in local memory
2650 */
2651 SUTIL_INLINE SUTIL_HOSTDEVICE void setByIndex(ULONGLONG4& v, int i, unsigned long long x)
2652 {
2653     ((unsigned long long*)(&v))[i] = x;
2654 }
2655 
2656 
2657 /******************************************************************************/
2658 
2659 /** Narrowing functions
2660 * @{
2661 */
2662 SUTIL_INLINE SUTIL_HOSTDEVICE int2 make_int2(const int3& v0) { return make_int2( v0.x, v0.y ); }
2663 SUTIL_INLINE SUTIL_HOSTDEVICE int2 make_int2(const int4& v0) { return make_int2( v0.x, v0.y ); }
2664 SUTIL_INLINE SUTIL_HOSTDEVICE int3 make_int3(const int4& v0) { return make_int3( v0.x, v0.y, v0.z ); }
2665 SUTIL_INLINE SUTIL_HOSTDEVICE uint2 make_uint2(const uint3& v0) { return make_uint2( v0.x, v0.y ); }
2666 SUTIL_INLINE SUTIL_HOSTDEVICE uint2 make_uint2(const uint4& v0) { return make_uint2( v0.x, v0.y ); }
2667 SUTIL_INLINE SUTIL_HOSTDEVICE uint3 make_uint3(const uint4& v0) { return make_uint3( v0.x, v0.y, v0.z ); }
2668 SUTIL_INLINE SUTIL_HOSTDEVICE longlong2 make_longlong2(const longlong3& v0) { return make_longlong2( v0.x, v0.y ); }
2669 SUTIL_INLINE SUTIL_HOSTDEVICE longlong2 make_longlong2(const LONGLONG4& v0) { return make_longlong2( v0.x, v0.y ); }
2670 SUTIL_INLINE SUTIL_HOSTDEVICE longlong3 make_longlong3(const LONGLONG4& v0) { return make_longlong3( v0.x, v0.y, v0.z ); }
2671 SUTIL_INLINE SUTIL_HOSTDEVICE ulonglong2 make_ulonglong2(const ulonglong3& v0) { return make_ulonglong2( v0.x, v0.y ); }
2672 SUTIL_INLINE SUTIL_HOSTDEVICE ulonglong2 make_ulonglong2(const ULONGLONG4& v0) { return make_ulonglong2( v0.x, v0.y ); }
2673 SUTIL_INLINE SUTIL_HOSTDEVICE ulonglong3 make_ulonglong3(const ULONGLONG4& v0) { return make_ulonglong3( v0.x, v0.y, v0.z ); }
2674 SUTIL_INLINE SUTIL_HOSTDEVICE float2 make_float2(const float3& v0) { return make_float2( v0.x, v0.y ); }
2675 SUTIL_INLINE SUTIL_HOSTDEVICE float2 make_float2(const float4& v0) { return make_float2( v0.x, v0.y ); }
2676 SUTIL_INLINE SUTIL_HOSTDEVICE float3 make_float3(const float4& v0) { return make_float3( v0.x, v0.y, v0.z ); }
2677 /** @} */
2678 
2679 /** Assemble functions from smaller vectors
2680 * @{
2681 */
2682 SUTIL_INLINE SUTIL_HOSTDEVICE int3 make_int3(const int v0, const int2& v1) { return make_int3( v0, v1.x, v1.y ); }
2683 SUTIL_INLINE SUTIL_HOSTDEVICE int3 make_int3(const int2& v0, const int v1) { return make_int3( v0.x, v0.y, v1 ); }
2684 SUTIL_INLINE SUTIL_HOSTDEVICE int4 make_int4(const int v0, const int v1, const int2& v2) { return make_int4( v0, v1, v2.x, v2.y ); }
2685 SUTIL_INLINE SUTIL_HOSTDEVICE int4 make_int4(const int v0, const int2& v1, const int v2) { return make_int4( v0, v1.x, v1.y, v2 ); }
2686 SUTIL_INLINE SUTIL_HOSTDEVICE int4 make_int4(const int2& v0, const int v1, const int v2) { return make_int4( v0.x, v0.y, v1, v2 ); }
2687 SUTIL_INLINE SUTIL_HOSTDEVICE int4 make_int4(const int v0, const int3& v1) { return make_int4( v0, v1.x, v1.y, v1.z ); }
2688 SUTIL_INLINE SUTIL_HOSTDEVICE int4 make_int4(const int3& v0, const int v1) { return make_int4( v0.x, v0.y, v0.z, v1 ); }
2689 SUTIL_INLINE SUTIL_HOSTDEVICE int4 make_int4(const int2& v0, const int2& v1) { return make_int4( v0.x, v0.y, v1.x, v1.y ); }
2690 SUTIL_INLINE SUTIL_HOSTDEVICE uint3 make_uint3(const unsigned int v0, const uint2& v1) { return make_uint3( v0, v1.x, v1.y ); }
2691 SUTIL_INLINE SUTIL_HOSTDEVICE uint3 make_uint3(const uint2& v0, const unsigned int v1) { return make_uint3( v0.x, v0.y, v1 ); }
2692 SUTIL_INLINE SUTIL_HOSTDEVICE uint4 make_uint4(const unsigned int v0, const unsigned int v1, const uint2& v2) { return make_uint4( v0, v1, v2.x, v2.y ); }
2693 SUTIL_INLINE SUTIL_HOSTDEVICE uint4 make_uint4(const unsigned int v0, const uint2& v1, const unsigned int v2) { return make_uint4( v0, v1.x, v1.y, v2 ); }
2694 SUTIL_INLINE SUTIL_HOSTDEVICE uint4 make_uint4(const uint2& v0, const unsigned int v1, const unsigned int v2) { return make_uint4( v0.x, v0.y, v1, v2 ); }
2695 SUTIL_INLINE SUTIL_HOSTDEVICE uint4 make_uint4(const unsigned int v0, const uint3& v1) { return make_uint4( v0, v1.x, v1.y, v1.z ); }
2696 SUTIL_INLINE SUTIL_HOSTDEVICE uint4 make_uint4(const uint3& v0, const unsigned int v1) { return make_uint4( v0.x, v0.y, v0.z, v1 ); }
2697 SUTIL_INLINE SUTIL_HOSTDEVICE uint4 make_uint4(const uint2& v0, const uint2& v1) { return make_uint4( v0.x, v0.y, v1.x, v1.y ); }
2698 SUTIL_INLINE SUTIL_HOSTDEVICE longlong3 make_longlong3(const long long v0, const longlong2& v1) { return make_longlong3(v0, v1.x, v1.y); }
2699 SUTIL_INLINE SUTIL_HOSTDEVICE longlong3 make_longlong3(const longlong2& v0, const long long v1) { return make_longlong3(v0.x, v0.y, v1); }
2700 SUTIL_INLINE SUTIL_HOSTDEVICE LONGLONG4 MAKE_LONGLONG4(const long long v0, const long long v1, const longlong2& v2) { return MAKE_LONGLONG4(v0, v1, v2.x, v2.y); }
2701 SUTIL_INLINE SUTIL_HOSTDEVICE LONGLONG4 MAKE_LONGLONG4(const long long v0, const longlong2& v1, const long long v2) { return MAKE_LONGLONG4(v0, v1.x, v1.y, v2); }
2702 SUTIL_INLINE SUTIL_HOSTDEVICE LONGLONG4 MAKE_LONGLONG4(const longlong2& v0, const long long v1, const long long v2) { return MAKE_LONGLONG4(v0.x, v0.y, v1, v2); }
2703 SUTIL_INLINE SUTIL_HOSTDEVICE LONGLONG4 MAKE_LONGLONG4(const long long v0, const longlong3& v1) { return MAKE_LONGLONG4(v0, v1.x, v1.y, v1.z); }
2704 SUTIL_INLINE SUTIL_HOSTDEVICE LONGLONG4 MAKE_LONGLONG4(const longlong3& v0, const long long v1) { return MAKE_LONGLONG4(v0.x, v0.y, v0.z, v1); }
2705 SUTIL_INLINE SUTIL_HOSTDEVICE LONGLONG4 MAKE_LONGLONG4(const longlong2& v0, const longlong2& v1) { return MAKE_LONGLONG4(v0.x, v0.y, v1.x, v1.y); }
2706 SUTIL_INLINE SUTIL_HOSTDEVICE ulonglong3 make_ulonglong3(const unsigned long long v0, const ulonglong2& v1) { return make_ulonglong3(v0, v1.x, v1.y); }
2707 SUTIL_INLINE SUTIL_HOSTDEVICE ulonglong3 make_ulonglong3(const ulonglong2& v0, const unsigned long long v1) { return make_ulonglong3(v0.x, v0.y, v1); }
2708 SUTIL_INLINE SUTIL_HOSTDEVICE ULONGLONG4 MAKE_ULONGLONG4(const unsigned long long v0, const unsigned long long v1, const ulonglong2& v2) { return MAKE_ULONGLONG4(v0, v1, v2.x, v2.y); }
2709 SUTIL_INLINE SUTIL_HOSTDEVICE ULONGLONG4 MAKE_ULONGLONG4(const unsigned long long v0, const ulonglong2& v1, const unsigned long long v2) { return MAKE_ULONGLONG4(v0, v1.x, v1.y, v2); }
2710 SUTIL_INLINE SUTIL_HOSTDEVICE ULONGLONG4 MAKE_ULONGLONG4(const ulonglong2& v0, const unsigned long long v1, const unsigned long long v2) { return MAKE_ULONGLONG4(v0.x, v0.y, v1, v2); }
2711 SUTIL_INLINE SUTIL_HOSTDEVICE ULONGLONG4 MAKE_ULONGLONG4(const unsigned long long v0, const ulonglong3& v1) { return MAKE_ULONGLONG4(v0, v1.x, v1.y, v1.z); }
2712 SUTIL_INLINE SUTIL_HOSTDEVICE ULONGLONG4 MAKE_ULONGLONG4(const ulonglong3& v0, const unsigned long long v1) { return MAKE_ULONGLONG4(v0.x, v0.y, v0.z, v1); }
2713 SUTIL_INLINE SUTIL_HOSTDEVICE ULONGLONG4 MAKE_ULONGLONG4(const ulonglong2& v0, const ulonglong2& v1) { return MAKE_ULONGLONG4(v0.x, v0.y, v1.x, v1.y); }
2714 SUTIL_INLINE SUTIL_HOSTDEVICE float3 make_float3(const float2& v0, const float v1) { return make_float3(v0.x, v0.y, v1); }
2715 SUTIL_INLINE SUTIL_HOSTDEVICE float3 make_float3(const float v0, const float2& v1) { return make_float3( v0, v1.x, v1.y ); }
2716 SUTIL_INLINE SUTIL_HOSTDEVICE float4 make_float4(const float v0, const float v1, const float2& v2) { return make_float4( v0, v1, v2.x, v2.y ); }
2717 SUTIL_INLINE SUTIL_HOSTDEVICE float4 make_float4(const float v0, const float2& v1, const float v2) { return make_float4( v0, v1.x, v1.y, v2 ); }
2718 SUTIL_INLINE SUTIL_HOSTDEVICE float4 make_float4(const float2& v0, const float v1, const float v2) { return make_float4( v0.x, v0.y, v1, v2 ); }
2719 SUTIL_INLINE SUTIL_HOSTDEVICE float4 make_float4(const float v0, const float3& v1) { return make_float4( v0, v1.x, v1.y, v1.z ); }
2720 SUTIL_INLINE SUTIL_HOSTDEVICE float4 make_float4(const float3& v0, const float v1) { return make_float4( v0.x, v0.y, v0.z, v1 ); }
2721 SUTIL_INLINE SUTIL_HOSTDEVICE float4 make_float4(const float2& v0, const float2& v1) { return make_float4( v0.x, v0.y, v1.x, v1.y ); }
2722 /** @} */
2723 
2724 
2725 
2726 
2727 #if defined(__CUDACC__) || defined(__CUDABE__)
2728 #else
2729 
2730 #include <iostream>
2731 #include <iomanip>
2732 #include <sstream>
2733 #include <vector>
2734 
2735 
2736 struct scuda
2737 {
2738     template<typename T>    // parse string into value
2739     static T  sval(const char* str );
2740 
2741     template<typename T>    // parse envvar into value
2742     static T  eval(const char* ekey, T fallback );
2743 
2744     template<typename T>    // parse string into vector
2745     static void   svec( std::vector<T>& v, const char* str, char delim=',' );
2746 
2747     template<typename T>    // parse envvar into vector
2748     static void   evec( std::vector<T>& v, const char* ekey, const char* fallback, char delim=',' );
2749 
2750     static float  efloat( const char* ekey, float fallback=0.f );
2751     static float3 efloat3(const char* ekey, const char* fallback="0,0,0",   char delim=',' );
2752     static float4 efloat4(const char* ekey, const char* fallback="0,0,0,0", char delim=',' );
2753     static float3 efloat3n(const char* ekey, const char* fallback="0,0,0",   char delim=',' );
2754 
2755     static std::string serialize( const float2& v );  // eg for metadata vector into string
2756     static std::string serialize( const float3& v );
2757     static std::string serialize( const float4& v );
2758 
2759     static float4 center_extent_( const float* mn, const float* mx );
2760     static float4 center_extent( const float3& mn, const float3& mx );
2761     static float4 center_extent( const float4& mn, const float4& mx );
2762 
2763 };
2764 
2765 template<typename T>
2766 inline T scuda::sval( const char* str )
2767 {
2768     std::string s(str) ;
2769     std::istringstream iss(s);
2770     T t ;
2771     iss >> t ;
2772     return t ;
2773 }
2774 
2775 template<typename T>
2776 inline T scuda::eval( const char* ekey, T fallback )
2777 {
2778     const char* str = getenv(ekey) ;
2779     return str ? sval<T>(str) : fallback ;
2780 }
2781 
2782 template<typename T>
2783 inline void scuda::svec(std::vector<T>& v , const char* str, char delim )
2784 {
2785     std::stringstream ss;
2786     ss.str(str)  ;
2787     std::string s;
2788     while (std::getline(ss, s, delim))
2789     {
2790         T t = sval<T>(s.c_str());
2791         v.push_back(t) ;
2792     }
2793 }
2794 
2795 template<typename T>
2796 inline void scuda::evec(std::vector<T>& v , const char* ekey, const char* fallback, char delim )
2797 {
2798     const char* str = getenv(ekey) ;
2799     svec(v, str ? str : fallback, delim );
2800 }
2801 
2802 inline float scuda::efloat(const char* ekey, float fallback)
2803 {
2804     return eval<float>(ekey, fallback);
2805 }
2806 
2807 inline float3 scuda::efloat3(const char* ekey, const char* fallback, char delim )
2808 {
2809    std::vector<float> fv ;
2810    evec(fv, ekey, fallback, delim );
2811    return make_float3(
2812               fv.size() > 0 ? fv[0] : 0.f ,
2813               fv.size() > 1 ? fv[1] : 0.f ,
2814               fv.size() > 2 ? fv[2] : 0.f
2815              );
2816 }
2817 
2818 inline float4 scuda::efloat4(const char* ekey, const char* fallback, char delim )
2819 {
2820    std::vector<float> fv ;
2821    evec(fv, ekey, fallback, delim );
2822    return make_float4(
2823               fv.size() > 0 ? fv[0] : 0.f ,
2824               fv.size() > 1 ? fv[1] : 0.f ,
2825               fv.size() > 2 ? fv[2] : 0.f ,
2826               fv.size() > 3 ? fv[3] : 0.f
2827              );
2828 }
2829 
2830 inline float3 scuda::efloat3n(const char* ekey, const char* fallback, char delim )
2831 {
2832    float3 v = efloat3(ekey, fallback, delim);
2833    return normalize(v);
2834 }
2835 
2836 
2837 
2838 inline std::string scuda::serialize(const float2& v )
2839 {
2840     std::stringstream ss ;
2841     ss << v.x
2842        << ","
2843        << v.y
2844        ;
2845     std::string str = ss.str();
2846     return str ;
2847 }
2848 
2849 inline std::string scuda::serialize(const float3& v )
2850 {
2851     std::stringstream ss ;
2852     ss << v.x
2853        << ","
2854        << v.y
2855        << ","
2856        << v.z
2857        ;
2858     std::string str = ss.str();
2859     return str ;
2860 }
2861 inline std::string scuda::serialize(const float4& v )
2862 {
2863     std::stringstream ss ;
2864     ss << v.x
2865        << ","
2866        << v.y
2867        << ","
2868        << v.z
2869        << ","
2870        << v.w
2871        ;
2872     std::string str = ss.str();
2873     return str ;
2874 }
2875 
2876 
2877 /**
2878 scuda::center_extent
2879 ----------------------
2880 
2881 The aim of center_extent "ce" is to define a box
2882 that contains all the points of a point cloud
2883 here defined by the mn and mx coordinate points.
2884 
2885 **/
2886 inline float4 scuda::center_extent_( const float* mn, const float* mx )
2887 {
2888     float3 center = make_float3( (mn[0]+mx[0])/2.f, (mn[1]+mx[1])/2.f, (mn[2]+mx[2])/2.f ) ;
2889     float3 mx_rel = make_float3( mx[0],mx[1],mx[2] ) - center ;
2890     float3 mn_rel = center - make_float3( mn[0],mn[1],mn[2] ) ;
2891     float extent = fmaxf( fmaxf(mx_rel), fmaxf(mn_rel) ) ;
2892     return make_float4( center, extent );
2893 }
2894 inline float4 scuda::center_extent( const float3& mn, const float3& mx )
2895 {
2896     return center_extent_(&mn.x, &mx.x);
2897 }
2898 inline float4 scuda::center_extent( const float4& mn, const float4& mx )
2899 {
2900     return center_extent_(&mn.x, &mx.x);
2901 }
2902 
2903 
2904 inline std::ostream& operator<<(std::ostream& os, const float2& v)
2905 {
2906     int w = 6 ;
2907     os
2908        << "("
2909        << std::setw(w) << std::fixed << std::setprecision(3) << v.x
2910        << ","
2911        << std::setw(w) << std::fixed << std::setprecision(3) << v.y
2912        << ") "
2913        ;
2914     return os;
2915 }
2916 
2917 
2918 
2919 
2920 inline std::ostream& operator<<(std::ostream& os, const float3& v)
2921 {
2922     int w = 6 ;
2923     os
2924        << "("
2925        << std::setw(w) << std::fixed << std::setprecision(3) << v.x
2926        << ","
2927        << std::setw(w) << std::fixed << std::setprecision(3) << v.y
2928        << ","
2929        << std::setw(w) << std::fixed << std::setprecision(3) << v.z
2930        << ") "
2931        ;
2932     return os;
2933 }
2934 
2935 inline std::ostream& operator<<(std::ostream& os, const float4& v)
2936 {
2937     int w = 6 ;
2938     os
2939        << "("
2940        << std::setw(w) << std::fixed << std::setprecision(3) << v.x
2941        << ","
2942        << std::setw(w) << std::fixed << std::setprecision(3) << v.y
2943        << ","
2944        << std::setw(w) << std::fixed << std::setprecision(3) << v.z
2945        << ","
2946        << std::setw(w) << std::fixed << std::setprecision(3) << v.w
2947        << ") "
2948        ;
2949     return os;
2950 }
2951 
2952 
2953 
2954 
2955 
2956 
2957 
2958 
2959 
2960 inline std::ostream& operator<<(std::ostream& os, const int2& v)
2961 {
2962     int w = 6 ;
2963     os
2964        << "("
2965        << std::setw(w) << v.x
2966        << ","
2967        << std::setw(w) << v.y
2968        << ") "
2969        ;
2970     return os;
2971 }
2972 
2973 inline std::ostream& operator<<(std::ostream& os, const int3& v)
2974 {
2975     int w = 6 ;
2976     os
2977        << "("
2978        << std::setw(w) << v.x
2979        << ","
2980        << std::setw(w) << v.y
2981        << ","
2982        << std::setw(w) << v.z
2983        << ") "
2984        ;
2985     return os;
2986 }
2987 
2988 inline std::ostream& operator<<(std::ostream& os, const int4& v)
2989 {
2990     int w = 6 ;
2991     os
2992        << "("
2993        << std::setw(w) << v.x
2994        << ","
2995        << std::setw(w) << v.y
2996        << ","
2997        << std::setw(w) << v.z
2998        << ","
2999        << std::setw(w) << v.w
3000        << ") "
3001        ;
3002     return os;
3003 }
3004 
3005 inline std::ostream& operator<<(std::ostream& os, const short4& v)
3006 {
3007     int w = 6 ;
3008     os
3009        << "("
3010        << std::setw(w) << v.x
3011        << ","
3012        << std::setw(w) << v.y
3013        << ","
3014        << std::setw(w) << v.z
3015        << ","
3016        << std::setw(w) << v.w
3017        << ") "
3018        ;
3019     return os;
3020 }
3021 
3022 inline std::ostream& operator<<(std::ostream& os, const uchar4& v)
3023 {
3024     int w = 4 ;
3025     os
3026        << "("
3027        << std::setw(w) << int(v.x)     // avoid trying to output char
3028        << ","
3029        << std::setw(w) << int(v.y)
3030        << ","
3031        << std::setw(w) << int(v.z)
3032        << ","
3033        << std::setw(w) << int(v.w)
3034        << ") "
3035        ;
3036     return os;
3037 }
3038 
3039 inline std::ostream& operator<<(std::ostream& os, const char4& v)
3040 {
3041     int w = 4 ;
3042     os
3043        << "("
3044        << std::setw(w) << int(v.x)     // avoid trying to output char
3045        << ","
3046        << std::setw(w) << int(v.y)
3047        << ","
3048        << std::setw(w) << int(v.z)
3049        << ","
3050        << std::setw(w) << int(v.w)
3051        << ") "
3052        ;
3053     return os;
3054 }
3055 
3056 
3057 
3058 
3059 inline std::ostream& operator<<(std::ostream& os, const uint3& v)
3060 {
3061     int w = 6 ;
3062     os
3063        << "("
3064        << std::setw(w) << v.x
3065        << ","
3066        << std::setw(w) << v.y
3067        << ","
3068        << std::setw(w) << v.z
3069        << ") "
3070        ;
3071     return os;
3072 }
3073 
3074 
3075 
3076 
3077 inline std::ostream& operator<<(std::ostream& os, const uint4& v)
3078 {
3079     int w = 6 ;
3080     os
3081        << "("
3082        << std::setw(w) << v.x
3083        << ","
3084        << std::setw(w) << v.y
3085        << ","
3086        << std::setw(w) << v.z
3087        << ","
3088        << std::setw(w) << v.w
3089        << ") "
3090        ;
3091     return os;
3092 }
3093 
3094 
3095 
3096 #endif