Manta Interactive Ray Tracer Development Mailing List

Text archives Help


[MANTA] r1228 - in trunk: Interface Model/Materials Model/Primitives


Chronological Thread 
  • From: bigler@sci.utah.edu
  • To: manta@sci.utah.edu
  • Subject: [MANTA] r1228 - in trunk: Interface Model/Materials Model/Primitives
  • Date: Thu, 26 Oct 2006 16:06:32 -0600 (MDT)

Author: bigler
Date: Thu Oct 26 16:06:31 2006
New Revision: 1228

Modified:
   trunk/Interface/RayPacket.h
   trunk/Model/Materials/Phong.cc
   trunk/Model/Primitives/Sphere.cc
Log:

Interface/RayPacket.h

  Added hitFinal, hitWithMask, hitWithoutTminCheck, hit (with no
  mask), wereNotHitSSE, and wereHitSSE.

Model/Materials/Phong.cc

  Replaced shadow ray hit mask with a call to wereNotHitSSE.

Model/Primitives/Sphere.cc

  Replaced hit registration code with calls to RayPacket hit
  functions.


Modified: trunk/Interface/RayPacket.h
==============================================================================
--- trunk/Interface/RayPacket.h (original)
+++ trunk/Interface/RayPacket.h Thu Oct 26 16:06:31 2006
@@ -451,10 +451,7 @@
     }
     bool hit(int which, Real t, const Material* matl, const Primitive* prim,
              const TexCoordMapper* tex) {
-
-      if(t < T_EPSILON)
-        return false;
-      if(t < data->minT[which]){
+      if(t > T_EPSILON && t < data->minT[which]){
         data->minT[which] = t;
         data->hitMatl[which] = matl;
         data->hitPrim[which] = prim;
@@ -464,10 +461,161 @@
         return false;
       }
     }
+#ifdef MANTA_SSE
+  private:
+    inline __m128 hitFinal(int start, __m128 mask, __m128 t,
+                           const Material* matl, const Primitive* prim,
+                           const TexCoordMapper* tex) {
+      mask = _mm_and_ps(mask, _mm_cmplt_ps(t, 
_mm_load_ps(&data->minT[start])));
+      int hit = _mm_movemask_ps(mask);
+      if(hit == 15){
+        // All of them hit, so we can store them all
+        _mm_store_ps(&data->minT[start], t);
+#ifdef __x86_64
+        // hitMatl
+        _mm_store_si128((__m128i*)&data->hitMatl[start], 
_mm_set1_epi64x((long long)matl));
+        _mm_store_si128((__m128i*)&data->hitMatl[start+2], 
_mm_set1_epi64x((long long)matl));
+        // hitPrim
+        _mm_store_si128((__m128i*)&data->hitPrim[start], 
_mm_set1_epi64x((long long)prim));
+        _mm_store_si128((__m128i*)&data->hitPrim[start+2], 
_mm_set1_epi64x((long long)prim));
+        // hitTex
+        _mm_store_si128((__m128i*)&data->hitTex[start], 
_mm_set1_epi64x((long long)tex));
+        _mm_store_si128((__m128i*)&data->hitTex[start+2], 
_mm_set1_epi64x((long long)tex));
+#else // __x86_64
+        _mm_store_si128((__m128i*)&data->hitMatl[start], 
_mm_set1_epi32((int)matl));
+        _mm_store_si128((__m128i*)&data->hitPrim[start], 
_mm_set1_epi32((int)prim));
+        _mm_store_si128((__m128i*)&data->hitTex[start], 
_mm_set1_epi32((int)tex));
+#endif // __x86_64
+      } else if(hit != 0){
+        // Some of them hit, some of them do not
+        // Intel has a masked move instruction but it seems to be really slow
+        // It is faster to load the old data and mask it in manually
+        _mm_store_ps(&data->minT[start], 
+                     _mm_or_ps(_mm_and_ps(mask, t),
+                               _mm_andnot_ps(mask, 
_mm_load_ps(&data->minT[start]))));
+#ifdef __x86_64
+        __m128i lomask = _mm_castps_si128(_mm_unpacklo_ps(mask, mask));
+        __m128i himask = _mm_castps_si128(_mm_unpackhi_ps(mask, mask));
+        // hitMatl
+        _mm_store_si128((__m128i*)&data->hitMatl[start],
+                        _mm_or_si128(_mm_and_si128(lomask, 
_mm_set1_epi64x((long long)matl)),
+                                     _mm_andnot_si128(lomask, 
_mm_load_si128((__m128i*)&data->hitMatl[start]))));
+        _mm_store_si128((__m128i*)&data->hitMatl[start+2],
+                        _mm_or_si128(_mm_and_si128(himask, 
_mm_set1_epi64x((long long)matl)),
+                                     _mm_andnot_si128(himask, 
_mm_load_si128((__m128i*)&data->hitMatl[start+2]))));
+        // hitPrim
+        _mm_store_si128((__m128i*)&data->hitPrim[start],
+                        _mm_or_si128(_mm_and_si128(lomask, 
_mm_set1_epi64x((long long)prim)),
+                                     _mm_andnot_si128(lomask, 
_mm_load_si128((__m128i*)&data->hitPrim[start]))));
+        _mm_store_si128((__m128i*)&data->hitPrim[start+2],
+                        _mm_or_si128(_mm_and_si128(himask, 
_mm_set1_epi64x((long long)prim)),
+                                     _mm_andnot_si128(himask, 
_mm_load_si128((__m128i*)&data->hitPrim[start+2]))));
+        // hitTex
+        _mm_store_si128((__m128i*)&data->hitTex[start],
+                        _mm_or_si128(_mm_and_si128(lomask, 
_mm_set1_epi64x((long long)tex)),
+                                     _mm_andnot_si128(lomask, 
_mm_load_si128((__m128i*)&data->hitTex[start]))));
+        _mm_store_si128((__m128i*)&data->hitTex[start+2],
+                        _mm_or_si128(_mm_and_si128(himask, 
_mm_set1_epi64x((long long)tex)),
+                                     _mm_andnot_si128(himask, 
_mm_load_si128((__m128i*)&data->hitTex[start+2]))));
+#else // __x86_64
+        __m128i imask = _mm_castps_si128(mask);
+        _mm_store_si128((__m128i*)&data->hitMatl[start],
+                        _mm_or_si128(_mm_and_si128(imask, 
_mm_set1_epi32((int)matl)),
+                                     _mm_andnot_si128(imask, 
_mm_load_si128((__m128i*)&data->hitMatl[start]))));
+        _mm_store_si128((__m128i*)&data->hitPrim[start],
+                        _mm_or_si128(_mm_and_si128(imask, 
_mm_set1_epi32((int)prim)),
+                                     _mm_andnot_si128(imask, 
_mm_load_si128((__m128i*)&data->hitPrim[start]))));
+        _mm_store_si128((__m128i*)&data->hitTex[start],
+                        _mm_or_si128(_mm_and_si128(imask, 
_mm_set1_epi32((int)tex)),
+                                     _mm_andnot_si128(imask, 
_mm_load_si128((__m128i*)&data->hitTex[start]))));
+#endif // __x86_64
+      }
+      return mask;
+    }
+  public:
+    //
+    // These are hit functions for SSE.  There are four versions: the
+    // first three have a mask for prior selections (one with a
+    // complemented mask).  The fourth has no mask.  Both call the
+    // above private function to do the bulk of the work.
+    //
+
+    // Mask is all ones for rays that actually hit, all zeros otherwise
+    inline __m128 hitWithMask(int start, __m128 mask, __m128 t,
+                              const Material* matl, const Primitive* prim,
+                              const TexCoordMapper* tex) {
+      mask = _mm_and_ps(mask, _mm_cmpgt_ps(t, _mm_set1_ps(T_EPSILON)));
+      return hitFinal(start, mask, t, matl, prim, tex);
+    }
+    // Mask is all zeros for days that actually hit, all ones otherwise
+    inline __m128 hitWithComplementedMask(int start, __m128 mask, __m128 t,
+                                          const Material* matl,
+                                          const Primitive* prim,
+                                          const TexCoordMapper* tex) {
+      mask = _mm_andnot_ps(mask, _mm_cmpgt_ps(t, _mm_set1_ps(T_EPSILON)));
+      return hitFinal(start, mask, t, matl, prim, tex);
+    }
+    // Mask is all ones for rays that actually hit, all zeros
+    // otherwise. It is assumed that mask already contains the results
+    // of checking that t > epsilon.
+    inline __m128 hitWithoutTminCheck(int start, __m128 mask, __m128 t,
+                                      const Material* matl,
+                                      const Primitive* prim,
+                                      const TexCoordMapper* tex) {
+      return hitFinal(start, mask, t, matl, prim, tex);
+    }
+    // No mask
+    inline __m128 hit(int start, __m128 t, const Material* matl,
+                    const Primitive* prim, const TexCoordMapper* tex) {
+      __m128 mask = _mm_cmpgt_ps(t, _mm_set1_ps(T_EPSILON));
+      return hitFinal(start, mask, t, matl, prim, tex);
+    }
+
+#endif // #ifdef MANTA_SSE
+      
     bool wasHit(int which)
     {
       return data->hitMatl[which] != 0;
     }
+
+#ifdef MANTA_SSE
+    ///////////////////////////////////////////////////////////
+    //
+    // Returns a SSE based mask for the rays that have hitMatl == 0
+    //
+    // We are using SSE integer instructions to avoid weird problems
+    // when casting pointers to floats and doing comparisons.
+    // Unfortunately, there aren't any != (cmpneq) integer
+    // instructions.  This is why the implementation is for
+    // wereNotHitSSE, and wereHitSSE takes the inverse of
+    // wereNotHitSSE.
+    //
+    // 32 bit: mask = (hitMatl == 0)
+    //
+    // 64 bit: mask = (hitMatl[low_bits] == 0) && (hitMatl[high_bits] == 0)
+    inline __m128 wereNotHitSSE(int start)
+    {
+#ifdef __x86_64
+      __m128 masklo = 
_mm_castsi128_ps(_mm_cmpeq_epi32(_mm_load_si128((__m128i*)&data->hitMatl[start]),
+                                                       _mm_setzero_si128()));
+      __m128 maskhi = 
_mm_castsi128_ps(_mm_cmpeq_epi32(_mm_load_si128((__m128i*)&data->hitMatl[start+2]),
+                                                       _mm_setzero_si128()));
+      return  _mm_and_ps(_mm_shuffle_ps(masklo, maskhi, _MM_SHUFFLE(2, 0, 2, 
0)),
+                         _mm_shuffle_ps(masklo, maskhi, _MM_SHUFFLE(3, 1, 3, 
1)));
+#else // __x86_64
+      return  
_mm_castsi128_ps(_mm_cmpeq_epi32(_mm_load_si128((__m128i*)&data->hitMatl[start]),
+                                               _mm_setzero_si128()));
+      
+#endif // __x86_64
+    }
+    ///////////////////////////////////////////////////////////
+    //
+    // Returns a SSE based mask for the rays that have hitMatl != 0
+    //
+    inline __m128 wereHitSSE(int start) {
+      return _mm_cmpeq_ps(wereNotHitSSE(start), _mm_setzero_ps());
+    }
+#endif // #ifdef MANTA_SSE
 
     void setHitMaterial(int which, const Material* matl)
     {

Modified: trunk/Model/Materials/Phong.cc
==============================================================================
--- trunk/Model/Materials/Phong.cc      (original)
+++ trunk/Model/Materials/Phong.cc      Thu Oct 26 16:06:31 2006
@@ -189,86 +189,9 @@
       RayPacketData* shadowData = shadowRays.data;
       for(;i<e;i+=4){
 
-        // A note about all of this.  We are trying to figure out
-        // which rays are zero.  This is done by checking the hitMatl
-        // pointer for being NULL or not.  If it is NULL then the
-        // shadow ray didn't hit anything and we need to compute the
-        // diffuse and specular components.
-        //
-        // The mask is a funny thing, where (if
-        // !shadowRays.hitMatl[i]) meant "add direct illumination",
-        // for the mask it is opposite.  0 is where we don't want to
-        // add DI.  This is done by comparing the hitMatl pointers
-        // with zero.  If they are 0 then set the mask bits on.
-        //
-        // The 64 bit stuff is harder.  There isn't a good way of
-        // doing 64 bit integer comparisons.  We tried to cast the
-        // pointers to doubles, but this didn't seem to work properly.
-        // Probably because when cast to doubles 0xFFFF...FF is NaN.
-        //
-        // So we do the comparisons on the two halves of the pointer.
-        // In these diagrams, FF represents "bit on" and 00 represents
-        // "bit off".  We need to combine the results of the pairs
-        // (done with the SHUFFLEs later and "and" operator).
-        //
-        // Shadow Pointer  Mask (X == 0)  Mask Composite Result (and)
-        // --------------  ------------- ----------------------
-        // FF FF           00 00         00
-        // FF 00           00 FF         00
-        // 00 FF           FF 00         00
-        // 00 00           FF FF         FF
-        //
-        // 32 bit
-        // FF              00
-        // 00              FF
-        //
-        // So with 64 bit both 32 bit halves need to be 00 for the
-        // hitMatl to be shaded.
-        //
-        // For 32 bit: (mask = !(ShadowPointer == 0) or (mask = 
!ShadowPointer)
-        //
-        // For 64 bit: (mask = !((SP[0] == 0) || (SP[1] == 0)) or
-        //             (mask = !(SP[0] || SP[1])               or
-        //             (mask = !SP[0] && !SP[1])  <- which is what we compute
-#ifdef __x86_64
-        // This is the golden code
+        // We are interested in the rays that didn't hit anything
+        __m128 mask = shadowRays.wereNotHitSSE(i);
         
-        __m128 masklo = 
cast_i2f(_mm_cmpeq_epi32(load44i((__m128i*)&shadowData->hitMatl[i]),
-                                                 _mm_setzero_si128()));
-        __m128 maskhi = 
cast_i2f(_mm_cmpeq_epi32(load44i((__m128i*)&shadowData->hitMatl[i+2]),
-                                                 _mm_setzero_si128()));
-        __m128 mask = _mm_and_ps(_mm_shuffle_ps(masklo, maskhi, 
_MM_SHUFFLE(2, 0, 2, 0)),
-                                 _mm_shuffle_ps(masklo, maskhi, 
_MM_SHUFFLE(3, 1, 3, 1)));
-        
-#else // __x86_64
-#ifndef SIMULATE_64BIT
-        __m128 mask = 
cast_i2f(_mm_cmpeq_epi32(load44i((__m128i*)&shadowData->hitMatl[i]), 
_mm_setzero_si128()));
-#else // SIMULATE_64BIT
-        __m128 mask;
-        {
-          bool debug = rays.getFlag(RayPacket::DebugPacket);
-          if (debug) { cerr << "mask  = ";simd_cerr(mask); }
-          
-          if (debug) { cerr << "mask2 = ";simd_cerr(mask); }
-          //        MANTA_ALIGN(16) int vals[8] = {0,0,0,0, 0,0,0,0};
-          MANTA_ALIGN(16) unsigned long long vals[4];
-          
-          for(int j = 0; j < 4; ++j)
-            vals[j] = (unsigned long long)(shadowData->hitMatl[i+j]);
-          __m128 masklo = 
cast_i2f(_mm_cmpeq_epi32(load44i((__m128i*)&vals[0]),
-                                                   _mm_setzero_si128()));
-          __m128 maskhi = 
cast_i2f(_mm_cmpeq_epi32(load44i((__m128i*)&vals[2]),
-                                                   _mm_setzero_si128()));
-          if (debug) { cerr << "masklo = ";simd_cerr(masklo); }
-          if (debug) { cerr << "maskhi = ";simd_cerr(maskhi); }
-          __m128 mask3 = _mm_and_ps(_mm_shuffle_ps(masklo, maskhi, 
_MM_SHUFFLE(2, 0, 2, 0)),
-                                    _mm_shuffle_ps(masklo, maskhi, 
_MM_SHUFFLE(3, 1, 3, 1)));
-          if (debug) { cerr << "mask3 = ";simd_cerr(mask3); cerr << "\n"; }
-          mask = mask3;
-        }
-#endif // SIMULATE_64BIT
-#endif // __x86_64
-
         if(_mm_movemask_ps(mask) == 0)
           continue;
         // Not in shadow, so compute the direct and specular contributions.

Modified: trunk/Model/Primitives/Sphere.cc
==============================================================================
--- trunk/Model/Primitives/Sphere.cc    (original)
+++ trunk/Model/Primitives/Sphere.cc    Thu Oct 26 16:06:31 2006
@@ -119,81 +119,16 @@
           // -(r+B)   The xor negates the value
           sse_t t0 = xor4(add4(r, B), cast_i2f(set4i(0x80000000)));
           sse_t hit0 = and4(hit, cmp4_gt(t0, set4(T_EPSILON)));
-          if(getmask4(hit0) != 0){
-            hit0 = and4(hit, cmp4_lt(t0, load44(&data->minT[i])));
-            if(getmask4(hit0) == 15){
-              store44(&data->minT[i], t0);
-#ifdef __x86_64
-              store44i((sse_int_t*)&data->hitMatl[i], set4l((long 
long)getMaterial()));
-              store44i((sse_int_t*)&data->hitMatl[i+2], set4l((long 
long)getMaterial()));
-              store44i((sse_int_t*)&data->hitPrim[i], set4l((long 
long)this));
-              store44i((sse_int_t*)&data->hitPrim[i+2], set4l((long 
long)this));
-              store44i((sse_int_t*)&data->hitTex[i], set4l((long 
long)getTexCoordMapper()));
-              store44i((sse_int_t*)&data->hitTex[i+2], set4l((long 
long)getTexCoordMapper()));
-#else
-              store44i((sse_int_t*)&data->hitMatl[i], 
set4i((int)getMaterial()));
-              store44i((sse_int_t*)&data->hitPrim[i], set4i((int)this));
-              store44i((sse_int_t*)&data->hitTex[i], 
set4i((int)getTexCoordMapper()));
-#endif
-            } else {
-              maskmove4i(cast_f2i(t0), cast_f2i(hit0), 
(char*)&data->minT[i]);
-#ifdef __x86_64
-              sse_int_t lohit = cast_f2i(unpacklo(hit0, hit0));
-              sse_int_t hihit = cast_f2i(unpackhi(hit0, hit0));
-              maskmove4i(set4l((long long)getMaterial()), lohit, 
(char*)&data->hitMatl[i]);
-              maskmove4i(set4l((long long)getMaterial()), hihit, 
(char*)&data->hitMatl[i+2]);
+          rays.hitWithoutTminCheck(i, hit0, t0, getMaterial(), this, 
getTexCoordMapper());
 
-              maskmove4i(set4l((long long)this), lohit, 
(char*)&data->hitPrim[i]);
-              maskmove4i(set4l((long long)this), hihit, 
(char*)&data->hitPrim[i+2]);
-              maskmove4i(set4l((long long)getTexCoordMapper()), lohit, 
(char*)&data->hitTex[i]);
-              maskmove4i(set4l((long long)getTexCoordMapper()), hihit, 
(char*)&data->hitTex[i+2]);
-#else
-              maskmove4i(set4i((int)getMaterial()), cast_f2i(hit0), 
(char*)&data->hitMatl[i]);
-              maskmove4i(set4i((int)this), cast_f2i(hit0), 
(char*)&data->hitPrim[i]);
-              maskmove4i(set4i((int)getTexCoordMapper()), cast_f2i(hit0), 
(char*)&data->hitTex[i]);
-#endif
-            }
-            // Mask off rays that successfully hit at t0
-            hit = _mm_andnot_ps(hit, hit0);
-            if(getmask4(hit) == 0)
-              continue;
-          }
+          hit = andnot4(hit0, hit);
+          // Rays that successfully hit at t0 are masked off
+          if(getmask4(hit) == 0)
+            continue;
 
           sse_t t1 = sub4(r, B);
           sse_t hit1 = and4(hit, cmp4_gt(t1, set4(T_EPSILON)));
-          hit1 = and4(hit1, cmp4_lt(t1, load44(&data->minT[i])));
-          if(getmask4(hit1) == 15){
-            store44(&data->minT[i], t1);
-#ifdef __x86_64
-            store44i((sse_int_t*)&data->hitMatl[i], set4l((long 
long)getMaterial()));
-            store44i((sse_int_t*)&data->hitMatl[i+2], set4l((long 
long)getMaterial()));
-            store44i((sse_int_t*)&data->hitPrim[i], set4l((long long)this));
-            store44i((sse_int_t*)&data->hitPrim[i+2], set4l((long 
long)this));
-            store44i((sse_int_t*)&data->hitTex[i], set4l((long 
long)getTexCoordMapper()));
-            store44i((sse_int_t*)&data->hitTex[i+2], set4l((long 
long)getTexCoordMapper()));
-#else
-            store44i((sse_int_t*)&data->hitMatl[i], 
set4i((int)getMaterial()));
-            store44i((sse_int_t*)&data->hitPrim[i], set4i((int)this));
-            store44i((sse_int_t*)&data->hitTex[i], 
set4i((int)getTexCoordMapper()));
-#endif
-          } else {
-            maskmove4i(cast_f2i(t1), cast_f2i(hit1), (char*)&data->minT[i]);
-#ifdef __x86_64
-            sse_int_t lohit = cast_f2i(unpacklo(hit1, hit1));
-            sse_int_t hihit = cast_f2i(unpackhi(hit1, hit1));
-            maskmove4i(set4l((long long)getMaterial()), lohit, 
(char*)&data->hitMatl[i]);
-            maskmove4i(set4l((long long)getMaterial()), hihit, 
(char*)&data->hitMatl[i+2]);
-
-            maskmove4i(set4l((long long)this), lohit, 
(char*)&data->hitPrim[i]);
-            maskmove4i(set4l((long long)this), hihit, 
(char*)&data->hitPrim[i+2]);
-            maskmove4i(set4l((long long)getTexCoordMapper()), lohit, 
(char*)&data->hitTex[i]);
-            maskmove4i(set4l((long long)getTexCoordMapper()), hihit, 
(char*)&data->hitTex[i+2]);
-#else
-            maskmove4i(set4i((int)getMaterial()), cast_f2i(hit1), 
(char*)&data->hitMatl[i]);
-            maskmove4i(set4i((int)this), cast_f2i(hit1), 
(char*)&data->hitPrim[i]);
-            maskmove4i(set4i((int)getTexCoordMapper()), cast_f2i(hit1), 
(char*)&data->hitTex[i]);
-#endif
-          }
+          rays.hitWithoutTminCheck(i, hit1, t1, getMaterial(), this, 
getTexCoordMapper());
         }
         for(;i<rays.rayEnd;i++){
           Vector D(rays.getDirection(i));
@@ -314,81 +249,16 @@
           // -(r+B)   The xor negates the value
           sse_t t0 = xor4(add4(r, B), cast_i2f(set4i(0x80000000)));
           sse_t hit0 = and4(hit, cmp4_gt(t0, set4(T_EPSILON)));
-          if(getmask4(hit0) != 0){
-            hit0 = and4(hit, cmp4_lt(t0, load44(&data->minT[i])));
-            if(getmask4(hit0) == 15){
-              store44(&data->minT[i], t0);
-#ifdef __x86_64
-              store44i((sse_int_t*)&data->hitMatl[i], set4l((long 
long)getMaterial()));
-              store44i((sse_int_t*)&data->hitMatl[i+2], set4l((long 
long)getMaterial()));
-              store44i((sse_int_t*)&data->hitPrim[i], set4l((long 
long)this));
-              store44i((sse_int_t*)&data->hitPrim[i+2], set4l((long 
long)this));
-              store44i((sse_int_t*)&data->hitTex[i], set4l((long 
long)getTexCoordMapper()));
-              store44i((sse_int_t*)&data->hitTex[i+2], set4l((long 
long)getTexCoordMapper()));
-#else
-              store44i((sse_int_t*)&data->hitMatl[i], 
set4i((int)getMaterial()));
-              store44i((sse_int_t*)&data->hitPrim[i], set4i((int)this));
-              store44i((sse_int_t*)&data->hitTex[i], 
set4i((int)getTexCoordMapper()));
-#endif
-            } else {
-              maskmove4i(cast_f2i(t0), cast_f2i(hit0), 
(char*)&data->minT[i]);
-#ifdef __x86_64
-              sse_int_t lohit = cast_f2i(unpacklo(hit0, hit0));
-              sse_int_t hihit = cast_f2i(unpackhi(hit0, hit0));
-              maskmove4i(set4l((long long)getMaterial()), lohit, 
(char*)&data->hitMatl[i]);
-              maskmove4i(set4l((long long)getMaterial()), hihit, 
(char*)&data->hitMatl[i+2]);
+          rays.hitWithoutTminCheck(i, hit0, t0, getMaterial(), this, 
getTexCoordMapper());
 
-              maskmove4i(set4l((long long)this), lohit, 
(char*)&data->hitPrim[i]);
-              maskmove4i(set4l((long long)this), hihit, 
(char*)&data->hitPrim[i+2]);
-              maskmove4i(set4l((long long)getTexCoordMapper()), lohit, 
(char*)&data->hitTex[i]);
-              maskmove4i(set4l((long long)getTexCoordMapper()), hihit, 
(char*)&data->hitTex[i+2]);
-#else
-              maskmove4i(set4i((int)getMaterial()), cast_f2i(hit0), 
(char*)&data->hitMatl[i]);
-              maskmove4i(set4i((int)this), cast_f2i(hit0), 
(char*)&data->hitPrim[i]);
-              maskmove4i(set4i((int)getTexCoordMapper()), cast_f2i(hit0), 
(char*)&data->hitTex[i]);
-#endif
-            }
-            // Mask off rays that successfully hit at t0
-            hit = _mm_andnot_ps(hit, hit0);
-            if(getmask4(hit) == 0)
-              continue;
-          }
+          hit = andnot4(hit0, hit);
+          // Rays that successfully hit at t0 are masked off
+          if(getmask4(hit) == 0)
+            continue;
 
           sse_t t1 = sub4(r, B);
           sse_t hit1 = and4(hit, cmp4_gt(t1, set4(T_EPSILON)));
-          hit1 = and4(hit1, cmp4_lt(t1, load44(&data->minT[i])));
-          if(getmask4(hit1) == 15){
-            store44(&data->minT[i], t1);
-#ifdef __x86_64
-            store44i((sse_int_t*)&data->hitMatl[i], set4l((long 
long)getMaterial()));
-            store44i((sse_int_t*)&data->hitMatl[i+2], set4l((long 
long)getMaterial()));
-            store44i((sse_int_t*)&data->hitPrim[i], set4l((long long)this));
-            store44i((sse_int_t*)&data->hitPrim[i+2], set4l((long 
long)this));
-            store44i((sse_int_t*)&data->hitTex[i], set4l((long 
long)getTexCoordMapper()));
-            store44i((sse_int_t*)&data->hitTex[i+2], set4l((long 
long)getTexCoordMapper()));
-#else
-            store44i((sse_int_t*)&data->hitMatl[i], 
set4i((int)getMaterial()));
-            store44i((sse_int_t*)&data->hitPrim[i], set4i((int)this));
-            store44i((sse_int_t*)&data->hitTex[i], 
set4i((int)getTexCoordMapper()));
-#endif
-          } else {
-            maskmove4i(cast_f2i(t1), cast_f2i(hit1), (char*)&data->minT[i]);
-#ifdef __x86_64
-            sse_int_t lohit = cast_f2i(unpacklo(hit1, hit1));
-            sse_int_t hihit = cast_f2i(unpackhi(hit1, hit1));
-            maskmove4i(set4l((long long)getMaterial()), lohit, 
(char*)&data->hitMatl[i]);
-            maskmove4i(set4l((long long)getMaterial()), hihit, 
(char*)&data->hitMatl[i+2]);
-
-            maskmove4i(set4l((long long)this), lohit, 
(char*)&data->hitPrim[i]);
-            maskmove4i(set4l((long long)this), hihit, 
(char*)&data->hitPrim[i+2]);
-            maskmove4i(set4l((long long)getTexCoordMapper()), lohit, 
(char*)&data->hitTex[i]);
-            maskmove4i(set4l((long long)getTexCoordMapper()), hihit, 
(char*)&data->hitTex[i+2]);
-#else
-            maskmove4i(set4i((int)getMaterial()), cast_f2i(hit1), 
(char*)&data->hitMatl[i]);
-            maskmove4i(set4i((int)this), cast_f2i(hit1), 
(char*)&data->hitPrim[i]);
-            maskmove4i(set4i((int)getTexCoordMapper()), cast_f2i(hit1), 
(char*)&data->hitTex[i]);
-#endif
-          }
+          rays.hitWithoutTminCheck(i, hit1, t1, getMaterial(), this, 
getTexCoordMapper());
         }
         for(;i<rays.rayEnd;i++){
           Vector O(rays.getOrigin(i)-center);




  • [MANTA] r1228 - in trunk: Interface Model/Materials Model/Primitives, bigler, 10/26/2006

Archive powered by MHonArc 2.6.16.

Top of page