Cycles: don't count volume boundaries as transparent bounces.
[blender-staging.git] / intern / cycles / kernel / split / kernel_queue_enqueue.h
1 /*
2  * Copyright 2011-2016 Blender Foundation
3  *
4  * Licensed under the Apache License, Version 2.0 (the "License");
5  * you may not use this file except in compliance with the License.
6  * You may obtain a copy of the License at
7  *
8  * http://www.apache.org/licenses/LICENSE-2.0
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an "AS IS" BASIS,
12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  * See the License for the specific language governing permissions and
14  * limitations under the License.
15  */
16
17 CCL_NAMESPACE_BEGIN
18
19 /* This kernel enqueues rays of different ray state into their
20  * appropriate queues:
21  *
22  * 1. Rays that have been determined to hit the background from the
23  *    "kernel_scene_intersect" kernel are enqueued in
24  *    QUEUE_HITBG_BUFF_UPDATE_TOREGEN_RAYS;
25  * 2. Rays that have been determined to be actively participating in pat
26  *    -iteration will be enqueued into QUEUE_ACTIVE_AND_REGENERATED_RAYS.
27  *
28  * State of queue during other times this kernel is called:
29  * At entry,
30  *   - QUEUE_ACTIVE_AND_REGENERATED_RAYS will be empty.
31  *   - QUEUE_HITBG_BUFF_UPDATE_TOREGEN_RAYS will contain RAY_TO_REGENERATE
32  *     and RAY_UPDATE_BUFFER rays.
33  * At exit,
34  *   - QUEUE_ACTIVE_AND_REGENERATED_RAYS will be filled with RAY_ACTIVE rays.
35  *   - QUEUE_HITBG_BUFF_UPDATE_TOREGEN_RAYS will be filled with
36  *     RAY_TO_REGENERATE, RAY_UPDATE_BUFFER, RAY_HIT_BACKGROUND rays.
37  */
38 ccl_device void kernel_queue_enqueue(KernelGlobals *kg,
39                                      ccl_local_param QueueEnqueueLocals *locals)
40 {
41         /* We have only 2 cases (Hit/Not-Hit) */
42         int lidx = ccl_local_id(1) * ccl_local_size(0) + ccl_local_id(0);
43         int ray_index = ccl_global_id(1) * ccl_global_size(0) + ccl_global_id(0);
44
45         if(lidx == 0) {
46                 locals->queue_atomics[0] = 0;
47                 locals->queue_atomics[1] = 0;
48         }
49         ccl_barrier(CCL_LOCAL_MEM_FENCE);
50
51         int queue_number = -1;
52
53         if(IS_STATE(kernel_split_state.ray_state, ray_index, RAY_HIT_BACKGROUND) ||
54            IS_STATE(kernel_split_state.ray_state, ray_index, RAY_UPDATE_BUFFER) ||
55            IS_STATE(kernel_split_state.ray_state, ray_index, RAY_TO_REGENERATE)) {
56                 queue_number = QUEUE_HITBG_BUFF_UPDATE_TOREGEN_RAYS;
57         }
58         else if(IS_STATE(kernel_split_state.ray_state, ray_index, RAY_ACTIVE) ||
59                 IS_STATE(kernel_split_state.ray_state, ray_index, RAY_HAS_ONLY_VOLUME) ||
60                 IS_STATE(kernel_split_state.ray_state, ray_index, RAY_REGENERATED)) {
61                 queue_number = QUEUE_ACTIVE_AND_REGENERATED_RAYS;
62         }
63
64         unsigned int my_lqidx;
65         if(queue_number != -1) {
66                 my_lqidx = get_local_queue_index(queue_number, locals->queue_atomics);
67         }
68         ccl_barrier(CCL_LOCAL_MEM_FENCE);
69
70         if(lidx == 0) {
71                 locals->queue_atomics[QUEUE_ACTIVE_AND_REGENERATED_RAYS] =
72                         get_global_per_queue_offset(QUEUE_ACTIVE_AND_REGENERATED_RAYS,
73                                                     locals->queue_atomics,
74                                                     kernel_split_params.queue_index);
75                 locals->queue_atomics[QUEUE_HITBG_BUFF_UPDATE_TOREGEN_RAYS] =
76                         get_global_per_queue_offset(QUEUE_HITBG_BUFF_UPDATE_TOREGEN_RAYS,
77                                                     locals->queue_atomics,
78                                                     kernel_split_params.queue_index);
79         }
80         ccl_barrier(CCL_LOCAL_MEM_FENCE);
81
82         unsigned int my_gqidx;
83         if(queue_number != -1) {
84                 my_gqidx = get_global_queue_index(queue_number,
85                                                   kernel_split_params.queue_size,
86                                                   my_lqidx,
87                                                   locals->queue_atomics);
88                 kernel_split_state.queue_data[my_gqidx] = ray_index;
89         }
90 }
91
92 CCL_NAMESPACE_END