From 5719ed122517d3d053b3c7c89a62c4f6b8eb8057 Mon Sep 17 00:00:00 2001 From: Sergey Sharybin Date: Mon, 12 Jan 2015 02:04:35 +0500 Subject: [PATCH] Cycles: Add leaf primitives sanity check asserts to the kernel This way we'll notice that leaf splitting didn't happen correct pretty easily in debug builds. There'll be absolutely no impact on release builds. --- intern/cycles/kernel/geom/geom_bvh_shadow.h | 2 ++ intern/cycles/kernel/geom/geom_bvh_subsurface.h | 2 ++ intern/cycles/kernel/geom/geom_bvh_traversal.h | 3 +++ intern/cycles/kernel/geom/geom_bvh_volume.h | 3 +++ intern/cycles/kernel/geom/geom_qbvh_shadow.h | 2 ++ intern/cycles/kernel/geom/geom_qbvh_subsurface.h | 2 ++ intern/cycles/kernel/geom/geom_qbvh_traversal.h | 9 ++++++--- intern/cycles/kernel/geom/geom_qbvh_volume.h | 3 +++ 8 files changed, 23 insertions(+), 3 deletions(-) diff --git a/intern/cycles/kernel/geom/geom_bvh_shadow.h b/intern/cycles/kernel/geom/geom_bvh_shadow.h index 5c87fe83172..193f49074a3 100644 --- a/intern/cycles/kernel/geom/geom_bvh_shadow.h +++ b/intern/cycles/kernel/geom/geom_bvh_shadow.h @@ -216,6 +216,8 @@ ccl_device bool BVH_FUNCTION_FULL_NAME(BVH)(KernelGlobals *kg, /* primitive intersection */ while(primAddr < primAddr2) { + kernel_assert(kernel_tex_fetch(__prim_type, primAddr) == type); + bool hit; /* todo: specialized intersect functions which don't fill in diff --git a/intern/cycles/kernel/geom/geom_bvh_subsurface.h b/intern/cycles/kernel/geom/geom_bvh_subsurface.h index 2f078d51985..290297ef5c5 100644 --- a/intern/cycles/kernel/geom/geom_bvh_subsurface.h +++ b/intern/cycles/kernel/geom/geom_bvh_subsurface.h @@ -205,6 +205,7 @@ ccl_device uint BVH_FUNCTION_FULL_NAME(BVH)(KernelGlobals *kg, case PRIMITIVE_TRIANGLE: { /* intersect ray against primitive */ for(; primAddr < primAddr2; primAddr++) { + kernel_assert(kernel_tex_fetch(__prim_type, primAddr) == type); /* only primitives from the same object */ uint tri_object = (object == OBJECT_NONE)? kernel_tex_fetch(__prim_object, primAddr): object; if(tri_object != subsurface_object) @@ -217,6 +218,7 @@ ccl_device uint BVH_FUNCTION_FULL_NAME(BVH)(KernelGlobals *kg, case PRIMITIVE_MOTION_TRIANGLE: { /* intersect ray against primitive */ for(; primAddr < primAddr2; primAddr++) { + kernel_assert(kernel_tex_fetch(__prim_type, primAddr) == type); /* only primitives from the same object */ uint tri_object = (object == OBJECT_NONE)? kernel_tex_fetch(__prim_object, primAddr): object; if(tri_object != subsurface_object) diff --git a/intern/cycles/kernel/geom/geom_bvh_traversal.h b/intern/cycles/kernel/geom/geom_bvh_traversal.h index da3e7fa963d..0298e687de2 100644 --- a/intern/cycles/kernel/geom/geom_bvh_traversal.h +++ b/intern/cycles/kernel/geom/geom_bvh_traversal.h @@ -268,6 +268,7 @@ ccl_device bool BVH_FUNCTION_FULL_NAME(BVH)(KernelGlobals *kg, #if defined(__KERNEL_DEBUG__) isect->num_traversal_steps++; #endif + kernel_assert(kernel_tex_fetch(__prim_type, primAddr) == type); if(triangle_intersect(kg, &isect_precalc, isect, P, dir, visibility, object, primAddr)) { /* shadow ray early termination */ #if defined(__KERNEL_SSE2__) @@ -288,6 +289,7 @@ ccl_device bool BVH_FUNCTION_FULL_NAME(BVH)(KernelGlobals *kg, #if defined(__KERNEL_DEBUG__) isect->num_traversal_steps++; #endif + kernel_assert(kernel_tex_fetch(__prim_type, primAddr) == type); if(motion_triangle_intersect(kg, isect, P, dir, ray->time, visibility, object, primAddr)) { /* shadow ray early termination */ #if defined(__KERNEL_SSE2__) @@ -310,6 +312,7 @@ ccl_device bool BVH_FUNCTION_FULL_NAME(BVH)(KernelGlobals *kg, #if defined(__KERNEL_DEBUG__) isect->num_traversal_steps++; #endif + kernel_assert(kernel_tex_fetch(__prim_type, primAddr) == type); bool hit; if(kernel_data.curve.curveflags & CURVE_KN_INTERPOLATE) hit = bvh_cardinal_curve_intersect(kg, isect, P, dir, visibility, object, primAddr, ray->time, type, lcg_state, difl, extmax); diff --git a/intern/cycles/kernel/geom/geom_bvh_volume.h b/intern/cycles/kernel/geom/geom_bvh_volume.h index cf4221fb715..0862812a170 100644 --- a/intern/cycles/kernel/geom/geom_bvh_volume.h +++ b/intern/cycles/kernel/geom/geom_bvh_volume.h @@ -206,6 +206,7 @@ ccl_device bool BVH_FUNCTION_FULL_NAME(BVH)(KernelGlobals *kg, case PRIMITIVE_TRIANGLE: { /* intersect ray against primitive */ for(; primAddr < primAddr2; primAddr++) { + kernel_assert(kernel_tex_fetch(__prim_type, primAddr) == type); /* only primitives from volume object */ uint tri_object = (object == OBJECT_NONE)? kernel_tex_fetch(__prim_object, primAddr): object; int object_flag = kernel_tex_fetch(__object_flag, tri_object); @@ -220,6 +221,7 @@ ccl_device bool BVH_FUNCTION_FULL_NAME(BVH)(KernelGlobals *kg, case PRIMITIVE_MOTION_TRIANGLE: { /* intersect ray against primitive */ for(; primAddr < primAddr2; primAddr++) { + kernel_assert(kernel_tex_fetch(__prim_type, primAddr) == type); /* only primitives from volume object */ uint tri_object = (object == OBJECT_NONE)? kernel_tex_fetch(__prim_object, primAddr): object; int object_flag = kernel_tex_fetch(__object_flag, tri_object); @@ -236,6 +238,7 @@ ccl_device bool BVH_FUNCTION_FULL_NAME(BVH)(KernelGlobals *kg, case PRIMITIVE_MOTION_CURVE: { /* intersect ray against primitive */ for(; primAddr < primAddr2; primAddr++) { + kernel_assert(kernel_tex_fetch(__prim_type, primAddr) == type); /* only primitives from volume object */ uint tri_object = (object == OBJECT_NONE)? kernel_tex_fetch(__prim_object, primAddr): object; int object_flag = kernel_tex_fetch(__object_flag, tri_object); diff --git a/intern/cycles/kernel/geom/geom_qbvh_shadow.h b/intern/cycles/kernel/geom/geom_qbvh_shadow.h index f43ced8f8f0..e77e220c919 100644 --- a/intern/cycles/kernel/geom/geom_qbvh_shadow.h +++ b/intern/cycles/kernel/geom/geom_qbvh_shadow.h @@ -225,6 +225,8 @@ ccl_device bool BVH_FUNCTION_FULL_NAME(QBVH)(KernelGlobals *kg, /* Primitive intersection. */ while(primAddr < primAddr2) { + kernel_assert(kernel_tex_fetch(__prim_type, primAddr) == type); + bool hit; /* todo: specialized intersect functions which don't fill in diff --git a/intern/cycles/kernel/geom/geom_qbvh_subsurface.h b/intern/cycles/kernel/geom/geom_qbvh_subsurface.h index 7d049e4941d..ef1754e711c 100644 --- a/intern/cycles/kernel/geom/geom_qbvh_subsurface.h +++ b/intern/cycles/kernel/geom/geom_qbvh_subsurface.h @@ -214,6 +214,7 @@ ccl_device uint BVH_FUNCTION_FULL_NAME(QBVH)(KernelGlobals *kg, case PRIMITIVE_TRIANGLE: { /* Intersect ray against primitive, */ for(; primAddr < primAddr2; primAddr++) { + kernel_assert(kernel_tex_fetch(__prim_type, primAddr) == type); /* Only primitives from the same object. */ uint tri_object = (object == OBJECT_NONE)? kernel_tex_fetch(__prim_object, primAddr): object; if(tri_object != subsurface_object) { @@ -227,6 +228,7 @@ ccl_device uint BVH_FUNCTION_FULL_NAME(QBVH)(KernelGlobals *kg, case PRIMITIVE_MOTION_TRIANGLE: { /* Intersect ray against primitive. */ for(; primAddr < primAddr2; primAddr++) { + kernel_assert(kernel_tex_fetch(__prim_type, primAddr) == type); /* Only primitives from the same object. */ uint tri_object = (object == OBJECT_NONE)? kernel_tex_fetch(__prim_object, primAddr): object; if(tri_object != subsurface_object) { diff --git a/intern/cycles/kernel/geom/geom_qbvh_traversal.h b/intern/cycles/kernel/geom/geom_qbvh_traversal.h index 4bc9e50d5df..64da51360de 100644 --- a/intern/cycles/kernel/geom/geom_qbvh_traversal.h +++ b/intern/cycles/kernel/geom/geom_qbvh_traversal.h @@ -285,10 +285,11 @@ ccl_device bool BVH_FUNCTION_FULL_NAME(QBVH)(KernelGlobals *kg, /* Primitive intersection. */ switch(type & PRIMITIVE_ALL) { case PRIMITIVE_TRIANGLE: { -#if defined(__KERNEL_DEBUG__) - isect->num_traversal_steps++; -#endif for(; primAddr < primAddr2; primAddr++) { +#if defined(__KERNEL_DEBUG__) + isect->num_traversal_steps++; +#endif + kernel_assert(kernel_tex_fetch(__prim_type, primAddr) == type); if(triangle_intersect(kg, &isect_precalc, isect, P, dir, visibility, object, primAddr)) { tfar = ssef(isect->t); /* Shadow ray early termination. */ @@ -304,6 +305,7 @@ ccl_device bool BVH_FUNCTION_FULL_NAME(QBVH)(KernelGlobals *kg, #if defined(__KERNEL_DEBUG__) isect->num_traversal_steps++; #endif + kernel_assert(kernel_tex_fetch(__prim_type, primAddr) == type); if(motion_triangle_intersect(kg, isect, P, dir, ray->time, visibility, object, primAddr)) { tfar = ssef(isect->t); /* Shadow ray early termination. */ @@ -321,6 +323,7 @@ ccl_device bool BVH_FUNCTION_FULL_NAME(QBVH)(KernelGlobals *kg, #if defined(__KERNEL_DEBUG__) isect->num_traversal_steps++; #endif + kernel_assert(kernel_tex_fetch(__prim_type, primAddr) == type); bool hit; if(kernel_data.curve.curveflags & CURVE_KN_INTERPOLATE) hit = bvh_cardinal_curve_intersect(kg, isect, P, dir, visibility, object, primAddr, ray->time, type, lcg_state, difl, extmax); diff --git a/intern/cycles/kernel/geom/geom_qbvh_volume.h b/intern/cycles/kernel/geom/geom_qbvh_volume.h index 8d4523c3486..a2a8d1a20ab 100644 --- a/intern/cycles/kernel/geom/geom_qbvh_volume.h +++ b/intern/cycles/kernel/geom/geom_qbvh_volume.h @@ -220,6 +220,7 @@ ccl_device bool BVH_FUNCTION_FULL_NAME(QBVH)(KernelGlobals *kg, switch(p_type) { case PRIMITIVE_TRIANGLE: { for(; primAddr < primAddr2; primAddr++) { + kernel_assert(kernel_tex_fetch(__prim_type, primAddr) == type); /* Only primitives from volume object. */ uint tri_object = (object == OBJECT_NONE)? kernel_tex_fetch(__prim_object, primAddr): object; int object_flag = kernel_tex_fetch(__object_flag, tri_object); @@ -234,6 +235,7 @@ ccl_device bool BVH_FUNCTION_FULL_NAME(QBVH)(KernelGlobals *kg, #if BVH_FEATURE(BVH_MOTION) case PRIMITIVE_MOTION_TRIANGLE: { for(; primAddr < primAddr2; primAddr++) { + kernel_assert(kernel_tex_fetch(__prim_type, primAddr) == type); /* Only primitives from volume object. */ uint tri_object = (object == OBJECT_NONE)? kernel_tex_fetch(__prim_object, primAddr): object; int object_flag = kernel_tex_fetch(__object_flag, tri_object); @@ -250,6 +252,7 @@ ccl_device bool BVH_FUNCTION_FULL_NAME(QBVH)(KernelGlobals *kg, case PRIMITIVE_CURVE: case PRIMITIVE_MOTION_CURVE: { for(; primAddr < primAddr2; primAddr++) { + kernel_assert(kernel_tex_fetch(__prim_type, primAddr) == type); /* Only primitives from volume object. */ uint tri_object = (object == OBJECT_NONE)? kernel_tex_fetch(__prim_object, primAddr): object; int object_flag = kernel_tex_fetch(__object_flag, tri_object);