Welcome to mirror list, hosted at ThFree Co, Russian Federation.

git.blender.org/blender.git - Unnamed repository; edit this file 'description' to name the repository.
summaryrefslogtreecommitdiff
path: root/intern
diff options
context:
space:
mode:
authorBrecht Van Lommel <brechtvanlommel@gmail.com>2017-09-14 23:56:32 +0300
committerBrecht Van Lommel <brechtvanlommel@gmail.com>2017-09-20 20:38:08 +0300
commit095a01a73a35d3af57573fc724d381bcca019f54 (patch)
tree3f22c746d1e9ae75365ade400ca08e0ae255788e /intern
parentb3afc8917cdeaa98ebfa3f2aa17e8c5a69fdb1e3 (diff)
Cycles: slightly improve BSDF sample stratification for path tracing.
Similar to what we did for area lights previously, this should help preserve stratification when using multiple BSDFs in theory. Improvements are not easily noticeable in practice though, because the number of BSDFs is usually low. Still nice to eliminate one sampling dimension.
Diffstat (limited to 'intern')
-rw-r--r--intern/cycles/kernel/kernel_bake.h11
-rw-r--r--intern/cycles/kernel/kernel_emission.h2
-rw-r--r--intern/cycles/kernel/kernel_path.h21
-rw-r--r--intern/cycles/kernel/kernel_path_branched.h4
-rw-r--r--intern/cycles/kernel/kernel_path_subsurface.h7
-rw-r--r--intern/cycles/kernel/kernel_path_volume.h8
-rw-r--r--intern/cycles/kernel/kernel_shader.h50
-rw-r--r--intern/cycles/kernel/kernel_shadow.h1
-rw-r--r--intern/cycles/kernel/kernel_subsurface.h3
-rw-r--r--intern/cycles/kernel/kernel_types.h26
-rw-r--r--intern/cycles/kernel/kernel_volume.h7
-rw-r--r--intern/cycles/kernel/split/kernel_shader_eval.h14
-rw-r--r--intern/cycles/kernel/split/kernel_subsurface_scatter.h13
13 files changed, 79 insertions, 88 deletions
diff --git a/intern/cycles/kernel/kernel_bake.h b/intern/cycles/kernel/kernel_bake.h
index b05f6e9ed5e..f06005c5072 100644
--- a/intern/cycles/kernel/kernel_bake.h
+++ b/intern/cycles/kernel/kernel_bake.h
@@ -51,8 +51,7 @@ ccl_device_inline void compute_light_pass(KernelGlobals *kg,
path_state_init(kg, &emission_sd, &state, rng_hash, sample, NULL);
/* evaluate surface shader */
- float rbsdf = path_state_rng_1D(kg, &state, PRNG_BSDF);
- shader_eval_surface(kg, sd, &state, rbsdf, state.flag);
+ shader_eval_surface(kg, sd, &state, state.flag);
/* TODO, disable more closures we don't need besides transparent */
shader_bsdf_disable_transparency(kg, sd);
@@ -241,12 +240,12 @@ ccl_device float3 kernel_bake_evaluate_direct_indirect(KernelGlobals *kg,
}
else {
/* surface color of the pass only */
- shader_eval_surface(kg, sd, state, 0.0f, 0);
+ shader_eval_surface(kg, sd, state, 0);
return kernel_bake_shader_bsdf(kg, sd, type);
}
}
else {
- shader_eval_surface(kg, sd, state, 0.0f, 0);
+ shader_eval_surface(kg, sd, state, 0);
color = kernel_bake_shader_bsdf(kg, sd, type);
}
@@ -338,7 +337,7 @@ ccl_device void kernel_bake_evaluate(KernelGlobals *kg, ccl_global uint4 *input,
case SHADER_EVAL_NORMAL:
{
if((sd.flag & SD_HAS_BUMP)) {
- shader_eval_surface(kg, &sd, &state, 0.f, 0);
+ shader_eval_surface(kg, &sd, &state, 0);
}
/* encoding: normal = (2 * color) - 1 */
@@ -352,7 +351,7 @@ ccl_device void kernel_bake_evaluate(KernelGlobals *kg, ccl_global uint4 *input,
}
case SHADER_EVAL_EMISSION:
{
- shader_eval_surface(kg, &sd, &state, 0.f, 0);
+ shader_eval_surface(kg, &sd, &state, 0);
out = shader_emissive_eval(kg, &sd);
break;
}
diff --git a/intern/cycles/kernel/kernel_emission.h b/intern/cycles/kernel/kernel_emission.h
index 13d4759a9ec..45b8c6311e1 100644
--- a/intern/cycles/kernel/kernel_emission.h
+++ b/intern/cycles/kernel/kernel_emission.h
@@ -70,7 +70,7 @@ ccl_device_noinline float3 direct_emissive_eval(KernelGlobals *kg,
/* no path flag, we're evaluating this for all closures. that's weak but
* we'd have to do multiple evaluations otherwise */
path_state_modify_bounce(state, true);
- shader_eval_surface(kg, emission_sd, state, 0.0f, 0);
+ shader_eval_surface(kg, emission_sd, state, 0);
path_state_modify_bounce(state, false);
/* evaluate emissive closure */
diff --git a/intern/cycles/kernel/kernel_path.h b/intern/cycles/kernel/kernel_path.h
index 86b2aa00776..2df21f1cda3 100644
--- a/intern/cycles/kernel/kernel_path.h
+++ b/intern/cycles/kernel/kernel_path.h
@@ -210,7 +210,7 @@ ccl_device_forceinline VolumeIntegrateResult kernel_path_volume(
/* indirect sample. if we use distance sampling and take just
* one sample for direct and indirect light, we could share
* this computation, but makes code a bit complex */
- float rphase = path_state_rng_1D(kg, state, PRNG_PHASE);
+ float rphase = path_state_rng_1D(kg, state, PRNG_PHASE_CHANNEL);
float rscatter = path_state_rng_1D(kg, state, PRNG_SCATTER_DISTANCE);
result = kernel_volume_decoupled_scatter(kg,
@@ -434,8 +434,7 @@ ccl_device void kernel_path_indirect(KernelGlobals *kg,
sd,
&isect,
ray);
- float rbsdf = path_state_rng_1D(kg, state, PRNG_BSDF);
- shader_eval_surface(kg, sd, state, rbsdf, state->flag);
+ shader_eval_surface(kg, sd, state, state->flag);
#ifdef __BRANCHED_PATH__
shader_merge_closures(sd);
#endif /* __BRANCHED_PATH__ */
@@ -483,17 +482,18 @@ ccl_device void kernel_path_indirect(KernelGlobals *kg,
/* bssrdf scatter to a different location on the same object, replacing
* the closures with a diffuse BSDF */
if(sd->flag & SD_BSSRDF) {
- const ShaderClosure *sc = shader_bssrdf_pick(sd, &throughput);
+ float bssrdf_u, bssrdf_v;
+ path_state_rng_2D(kg,
+ state,
+ PRNG_BSDF_U,
+ &bssrdf_u, &bssrdf_v);
+
+ const ShaderClosure *sc = shader_bssrdf_pick(sd, &throughput, &bssrdf_u);
/* do bssrdf scatter step if we picked a bssrdf closure */
if(sc) {
uint lcg_state = lcg_state_init(state, 0x68bc21eb);
- float bssrdf_u, bssrdf_v;
- path_state_rng_2D(kg,
- state,
- PRNG_BSDF_U,
- &bssrdf_u, &bssrdf_v);
subsurface_scatter_step(kg,
sd,
state,
@@ -587,8 +587,7 @@ ccl_device_forceinline void kernel_path_integrate(
/* Setup and evaluate shader. */
shader_setup_from_ray(kg, &sd, &isect, ray);
- float rbsdf = path_state_rng_1D(kg, state, PRNG_BSDF);
- shader_eval_surface(kg, &sd, state, rbsdf, state->flag);
+ shader_eval_surface(kg, &sd, state, state->flag);
/* Apply shadow catcher, holdout, emission. */
if(!kernel_path_shader_apply(kg,
diff --git a/intern/cycles/kernel/kernel_path_branched.h b/intern/cycles/kernel/kernel_path_branched.h
index e525e008945..010988d2a02 100644
--- a/intern/cycles/kernel/kernel_path_branched.h
+++ b/intern/cycles/kernel/kernel_path_branched.h
@@ -339,7 +339,7 @@ ccl_device void kernel_branched_path_integrate(KernelGlobals *kg,
/* scatter sample. if we use distance sampling and take just one
* sample for direct and indirect light, we could share this
* computation, but makes code a bit complex */
- float rphase = path_state_rng_1D(kg, &ps, PRNG_PHASE);
+ float rphase = path_state_rng_1D(kg, &ps, PRNG_PHASE_CHANNEL);
float rscatter = path_state_rng_1D(kg, &ps, PRNG_SCATTER_DISTANCE);
VolumeIntegrateResult result = kernel_volume_decoupled_scatter(kg,
@@ -439,7 +439,7 @@ ccl_device void kernel_branched_path_integrate(KernelGlobals *kg,
/* Setup and evaluate shader. */
shader_setup_from_ray(kg, &sd, &isect, &ray);
- shader_eval_surface(kg, &sd, &state, 0.0f, state.flag);
+ shader_eval_surface(kg, &sd, &state, state.flag);
shader_merge_closures(&sd);
/* Apply shadow catcher, holdout, emission. */
diff --git a/intern/cycles/kernel/kernel_path_subsurface.h b/intern/cycles/kernel/kernel_path_subsurface.h
index cc6231eb6b1..1753618607a 100644
--- a/intern/cycles/kernel/kernel_path_subsurface.h
+++ b/intern/cycles/kernel/kernel_path_subsurface.h
@@ -32,7 +32,10 @@ bool kernel_path_subsurface_scatter(
ccl_addr_space float3 *throughput,
ccl_addr_space SubsurfaceIndirectRays *ss_indirect)
{
- const ShaderClosure *sc = shader_bssrdf_pick(sd, throughput);
+ float bssrdf_u, bssrdf_v;
+ path_state_rng_2D(kg, state, PRNG_BSDF_U, &bssrdf_u, &bssrdf_v);
+
+ const ShaderClosure *sc = shader_bssrdf_pick(sd, throughput, &bssrdf_u);
/* do bssrdf scatter step if we picked a bssrdf closure */
if(sc) {
@@ -45,8 +48,6 @@ bool kernel_path_subsurface_scatter(
uint lcg_state = lcg_state_init_addrspace(state, 0x68bc21eb);
SubsurfaceIntersection ss_isect;
- float bssrdf_u, bssrdf_v;
- path_state_rng_2D(kg, state, PRNG_BSDF_U, &bssrdf_u, &bssrdf_v);
int num_hits = subsurface_scatter_multi_intersect(kg,
&ss_isect,
sd,
diff --git a/intern/cycles/kernel/kernel_path_volume.h b/intern/cycles/kernel/kernel_path_volume.h
index f645a109ce9..3cf897ac49c 100644
--- a/intern/cycles/kernel/kernel_path_volume.h
+++ b/intern/cycles/kernel/kernel_path_volume.h
@@ -77,7 +77,7 @@ bool kernel_path_volume_bounce(
float3 phase_omega_in;
differential3 phase_domega_in;
float phase_u, phase_v;
- path_state_rng_2D(kg, state, PRNG_PHASE_U, &phase_u, &phase_v);
+ path_state_rng_2D(kg, state, PRNG_BSDF_U, &phase_u, &phase_v);
int label;
label = shader_volume_phase_sample(kg, sd, phase_u, phase_v, &phase_eval,
@@ -155,7 +155,7 @@ ccl_device void kernel_branched_path_volume_connect_light(
float3 tp = throughput;
/* sample position on volume segment */
- float rphase = path_branched_rng_1D(kg, state->rng_hash, state, j, num_samples, PRNG_PHASE);
+ float rphase = path_branched_rng_1D(kg, state->rng_hash, state, j, num_samples, PRNG_PHASE_CHANNEL);
float rscatter = path_branched_rng_1D(kg, state->rng_hash, state, j, num_samples, PRNG_SCATTER_DISTANCE);
VolumeIntegrateResult result = kernel_volume_decoupled_scatter(kg,
@@ -201,7 +201,7 @@ ccl_device void kernel_branched_path_volume_connect_light(
float3 tp = throughput;
/* sample position on volume segment */
- float rphase = path_branched_rng_1D(kg, state->rng_hash, state, j, num_samples, PRNG_PHASE);
+ float rphase = path_branched_rng_1D(kg, state->rng_hash, state, j, num_samples, PRNG_PHASE_CHANNEL);
float rscatter = path_branched_rng_1D(kg, state->rng_hash, state, j, num_samples, PRNG_SCATTER_DISTANCE);
VolumeIntegrateResult result = kernel_volume_decoupled_scatter(kg,
@@ -238,7 +238,7 @@ ccl_device void kernel_branched_path_volume_connect_light(
float3 tp = throughput;
/* sample position on volume segment */
- float rphase = path_state_rng_1D(kg, state, PRNG_PHASE);
+ float rphase = path_state_rng_1D(kg, state, PRNG_PHASE_CHANNEL);
float rscatter = path_state_rng_1D(kg, state, PRNG_SCATTER_DISTANCE);
VolumeIntegrateResult result = kernel_volume_decoupled_scatter(kg,
diff --git a/intern/cycles/kernel/kernel_shader.h b/intern/cycles/kernel/kernel_shader.h
index 88aa1f712a4..5ef4475e259 100644
--- a/intern/cycles/kernel/kernel_shader.h
+++ b/intern/cycles/kernel/kernel_shader.h
@@ -575,7 +575,8 @@ void shader_bsdf_eval(KernelGlobals *kg,
}
}
-ccl_device_inline const ShaderClosure *shader_bsdf_pick(ShaderData *sd)
+ccl_device_inline const ShaderClosure *shader_bsdf_pick(ShaderData *sd,
+ float *randu)
{
int sampled = 0;
@@ -591,19 +592,25 @@ ccl_device_inline const ShaderClosure *shader_bsdf_pick(ShaderData *sd)
}
}
- float r = sd->randb_closure*sum;
+ float r = (*randu)*sum;
float partial_sum = 0.0f;
for(int i = 0; i < sd->num_closure; i++) {
const ShaderClosure *sc = &sd->closure[i];
if(CLOSURE_IS_BSDF(sc->type)) {
- partial_sum += sc->sample_weight;
+ float next_sum = partial_sum + sc->sample_weight;
- if(r <= partial_sum) {
+ if(r < next_sum) {
sampled = i;
+
+ /* Rescale to reuse for direction sample, to better
+ * preserve stratifaction. */
+ *randu = (r - partial_sum) / sc->sample_weight;
break;
}
+
+ partial_sum = next_sum;
}
}
}
@@ -612,7 +619,8 @@ ccl_device_inline const ShaderClosure *shader_bsdf_pick(ShaderData *sd)
}
ccl_device_inline const ShaderClosure *shader_bssrdf_pick(ShaderData *sd,
- ccl_addr_space float3 *throughput)
+ ccl_addr_space float3 *throughput,
+ float *randu)
{
int sampled = 0;
@@ -632,16 +640,16 @@ ccl_device_inline const ShaderClosure *shader_bssrdf_pick(ShaderData *sd,
}
}
- float r = sd->randb_closure*(sum_bsdf + sum_bssrdf);
+ float r = (*randu)*(sum_bsdf + sum_bssrdf);
float partial_sum = 0.0f;
for(int i = 0; i < sd->num_closure; i++) {
const ShaderClosure *sc = &sd->closure[i];
if(CLOSURE_IS_BSDF_OR_BSSRDF(sc->type)) {
- partial_sum += sc->sample_weight;
+ float next_sum = partial_sum + sc->sample_weight;
- if(r <= partial_sum) {
+ if(r < next_sum) {
if(CLOSURE_IS_BSDF(sc->type)) {
*throughput *= (sum_bsdf + sum_bssrdf) / sum_bsdf;
return NULL;
@@ -649,9 +657,15 @@ ccl_device_inline const ShaderClosure *shader_bssrdf_pick(ShaderData *sd,
else {
*throughput *= (sum_bsdf + sum_bssrdf) / sum_bssrdf;
sampled = i;
+
+ /* Rescale to reuse for direction sample, to better
+ * preserve stratifaction. */
+ *randu = (r - partial_sum) / sc->sample_weight;
break;
}
}
+
+ partial_sum = next_sum;
}
}
}
@@ -667,7 +681,7 @@ ccl_device_inline int shader_bsdf_sample(KernelGlobals *kg,
differential3 *domega_in,
float *pdf)
{
- const ShaderClosure *sc = shader_bsdf_pick(sd);
+ const ShaderClosure *sc = shader_bsdf_pick(sd, &randu);
if(!sc) {
*pdf = 0.0f;
return LABEL_NONE;
@@ -923,11 +937,10 @@ ccl_device float3 shader_holdout_eval(KernelGlobals *kg, ShaderData *sd)
/* Surface Evaluation */
ccl_device void shader_eval_surface(KernelGlobals *kg, ShaderData *sd,
- ccl_addr_space PathState *state, float randb, int path_flag)
+ ccl_addr_space PathState *state, int path_flag)
{
sd->num_closure = 0;
sd->num_closure_extra = 0;
- sd->randb_closure = randb;
#ifdef __OSL__
if(kg->osl)
@@ -958,7 +971,6 @@ ccl_device float3 shader_eval_background(KernelGlobals *kg, ShaderData *sd,
{
sd->num_closure = 0;
sd->num_closure_extra = 0;
- sd->randb_closure = 0.0f;
#ifdef __SVM__
#ifdef __OSL__
@@ -1040,17 +1052,22 @@ ccl_device int shader_volume_phase_sample(KernelGlobals *kg, const ShaderData *s
sum += sc->sample_weight;
}
- float r = sd->randb_closure*sum;
- sum = 0.0f;
+ float r = randu*sum;
+ float partial_sum = 0.0f;
for(sampled = 0; sampled < sd->num_closure; sampled++) {
const ShaderClosure *sc = &sd->closure[sampled];
if(CLOSURE_IS_PHASE(sc->type)) {
- sum += sc->sample_weight;
+ float next_sum = partial_sum + sc->sample_weight;
- if(r <= sum)
+ if(r <= next_sum) {
+ /* Rescale to reuse for BSDF direction sample. */
+ randu = (r - partial_sum) / sc->sample_weight;
break;
+ }
+
+ partial_sum = next_sum;
}
}
@@ -1154,7 +1171,6 @@ ccl_device void shader_eval_displacement(KernelGlobals *kg, ShaderData *sd, ccl_
{
sd->num_closure = 0;
sd->num_closure_extra = 0;
- sd->randb_closure = 0.0f;
/* this will modify sd->P */
#ifdef __SVM__
diff --git a/intern/cycles/kernel/kernel_shadow.h b/intern/cycles/kernel/kernel_shadow.h
index e02494ec1b0..065f9b184e2 100644
--- a/intern/cycles/kernel/kernel_shadow.h
+++ b/intern/cycles/kernel/kernel_shadow.h
@@ -86,7 +86,6 @@ ccl_device_forceinline bool shadow_handle_transparent_isect(
shader_eval_surface(kg,
shadow_sd,
state,
- 0.0f,
PATH_RAY_SHADOW);
path_state_modify_bounce(state, false);
*throughput *= shader_bsdf_transparency(kg, shadow_sd);
diff --git a/intern/cycles/kernel/kernel_subsurface.h b/intern/cycles/kernel/kernel_subsurface.h
index 027d59b5a4e..23a09e5e2ca 100644
--- a/intern/cycles/kernel/kernel_subsurface.h
+++ b/intern/cycles/kernel/kernel_subsurface.h
@@ -79,7 +79,6 @@ ccl_device_inline float3 subsurface_scatter_eval(ShaderData *sd,
ccl_device void subsurface_scatter_setup_diffuse_bsdf(ShaderData *sd, const ShaderClosure *sc, float3 weight, bool hit, float3 N)
{
sd->flag &= ~SD_CLOSURE_FLAGS;
- sd->randb_closure = 0.0f;
sd->num_closure = 0;
sd->num_closure_extra = 0;
@@ -155,7 +154,7 @@ ccl_device void subsurface_color_bump_blur(KernelGlobals *kg,
if(bump || texture_blur > 0.0f) {
/* average color and normal at incoming point */
- shader_eval_surface(kg, sd, state, 0.0f, state_flag);
+ shader_eval_surface(kg, sd, state, state_flag);
float3 in_color = shader_bssrdf_sum(sd, (bump)? N: NULL, NULL);
/* we simply divide out the average color and multiply with the average
diff --git a/intern/cycles/kernel/kernel_types.h b/intern/cycles/kernel/kernel_types.h
index 1b4e926ca28..1853fab1967 100644
--- a/intern/cycles/kernel/kernel_types.h
+++ b/intern/cycles/kernel/kernel_types.h
@@ -281,31 +281,21 @@ enum PathTraceDimension {
PRNG_FILTER_V = 1,
PRNG_LENS_U = 2,
PRNG_LENS_V = 3,
-#ifdef __CAMERA_MOTION__
PRNG_TIME = 4,
PRNG_UNUSED_0 = 5,
PRNG_UNUSED_1 = 6, /* for some reason (6, 7) is a bad sobol pattern */
PRNG_UNUSED_2 = 7, /* with a low number of samples (< 64) */
-#endif
- PRNG_BASE_NUM = 8,
+ PRNG_BASE_NUM = 10,
PRNG_BSDF_U = 0,
PRNG_BSDF_V = 1,
- PRNG_BSDF = 2,
- PRNG_UNUSED3 = 3,
- PRNG_LIGHT_U = 4,
- PRNG_LIGHT_V = 5,
- PRNG_LIGHT_TERMINATE = 6,
- PRNG_TERMINATE = 7,
-
-#ifdef __VOLUME__
- PRNG_PHASE_U = 8,
- PRNG_PHASE_V = 9,
- PRNG_PHASE = 10,
- PRNG_SCATTER_DISTANCE = 11,
-#endif
-
- PRNG_BOUNCE_NUM = 12,
+ PRNG_LIGHT_U = 2,
+ PRNG_LIGHT_V = 3,
+ PRNG_LIGHT_TERMINATE = 4,
+ PRNG_TERMINATE = 5,
+ PRNG_PHASE_CHANNEL = 6,
+ PRNG_SCATTER_DISTANCE = 7,
+ PRNG_BOUNCE_NUM = 8,
};
enum SamplingPattern {
diff --git a/intern/cycles/kernel/kernel_volume.h b/intern/cycles/kernel/kernel_volume.h
index bdaba2e2e4b..d9c310a893e 100644
--- a/intern/cycles/kernel/kernel_volume.h
+++ b/intern/cycles/kernel/kernel_volume.h
@@ -379,9 +379,8 @@ ccl_device VolumeIntegrateResult kernel_volume_integrate_homogeneous(
/* pick random color channel, we use the Veach one-sample
* model with balance heuristic for the channels */
- float rphase = path_state_rng_1D(kg, state, PRNG_PHASE);
+ float rphase = path_state_rng_1D(kg, state, PRNG_PHASE_CHANNEL);
int channel = (int)(rphase*3.0f);
- sd->randb_closure = rphase*3.0f - channel;
/* decide if we will hit or miss */
bool scatter = true;
@@ -484,9 +483,8 @@ ccl_device VolumeIntegrateResult kernel_volume_integrate_heterogeneous_distance(
/* pick random color channel, we use the Veach one-sample
* model with balance heuristic for the channels */
float xi = path_state_rng_1D(kg, state, PRNG_SCATTER_DISTANCE);
- float rphase = path_state_rng_1D(kg, state, PRNG_PHASE);
+ float rphase = path_state_rng_1D(kg, state, PRNG_PHASE_CHANNEL);
int channel = (int)(rphase*3.0f);
- sd->randb_closure = rphase*3.0f - channel;
bool has_scatter = false;
for(int i = 0; i < max_steps; i++) {
@@ -843,7 +841,6 @@ ccl_device VolumeIntegrateResult kernel_volume_decoupled_scatter(
/* pick random color channel, we use the Veach one-sample
* model with balance heuristic for the channels */
int channel = (int)(rphase*3.0f);
- sd->randb_closure = rphase*3.0f - channel;
float xi = rscatter;
/* probabilistic scattering decision based on transmittance */
diff --git a/intern/cycles/kernel/split/kernel_shader_eval.h b/intern/cycles/kernel/split/kernel_shader_eval.h
index 20bd211837e..c792c4adb0e 100644
--- a/intern/cycles/kernel/split/kernel_shader_eval.h
+++ b/intern/cycles/kernel/split/kernel_shader_eval.h
@@ -50,18 +50,8 @@ ccl_device void kernel_shader_eval(KernelGlobals *kg)
if(IS_STATE(ray_state, ray_index, RAY_ACTIVE)) {
ccl_global PathState *state = &kernel_split_state.path_state[ray_index];
-#ifndef __BRANCHED_PATH__
- float rbsdf = path_state_rng_1D(kg, state, PRNG_BSDF);
- shader_eval_surface(kg, &kernel_split_state.sd[ray_index], state, rbsdf, state->flag);
-#else
- float rbsdf = 0.0f;
-
- if(!kernel_data.integrator.branched || IS_FLAG(ray_state, ray_index, RAY_BRANCHED_INDIRECT)) {
- rbsdf = path_state_rng_1D(kg, state, PRNG_BSDF);
-
- }
-
- shader_eval_surface(kg, &kernel_split_state.sd[ray_index], state, rbsdf, state->flag);
+ shader_eval_surface(kg, &kernel_split_state.sd[ray_index], state, state->flag);
+#ifdef __BRANCHED_PATH__
shader_merge_closures(&kernel_split_state.sd[ray_index]);
#endif /* __BRANCHED_PATH__ */
}
diff --git a/intern/cycles/kernel/split/kernel_subsurface_scatter.h b/intern/cycles/kernel/split/kernel_subsurface_scatter.h
index 6caa18518dd..3b957856aea 100644
--- a/intern/cycles/kernel/split/kernel_subsurface_scatter.h
+++ b/intern/cycles/kernel/split/kernel_subsurface_scatter.h
@@ -250,16 +250,17 @@ ccl_device void kernel_subsurface_scatter(KernelGlobals *kg)
#ifdef __BRANCHED_PATH__
}
else if(IS_FLAG(ray_state, ray_index, RAY_BRANCHED_INDIRECT)) {
- const ShaderClosure *sc = shader_bssrdf_pick(sd, throughput);
+ float bssrdf_u, bssrdf_v;
+ path_state_rng_2D(kg,
+ state,
+ PRNG_BSDF_U,
+ &bssrdf_u, &bssrdf_v);
+
+ const ShaderClosure *sc = shader_bssrdf_pick(sd, throughput, &bssrdf_u);
/* do bssrdf scatter step if we picked a bssrdf closure */
if(sc) {
uint lcg_state = lcg_state_init_addrspace(state, 0x68bc21eb);
- float bssrdf_u, bssrdf_v;
- path_state_rng_2D(kg,
- state,
- PRNG_BSDF_U,
- &bssrdf_u, &bssrdf_v);
subsurface_scatter_step(kg,
sd,
state,