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
diff options
context:
space:
mode:
authorSergey Sharybin <sergey.vfx@gmail.com>2015-01-19 17:08:58 +0300
committerSergey Sharybin <sergey.vfx@gmail.com>2015-01-19 17:23:21 +0300
commit7fd4c440ec2207eb80be13bf14eefa940e39d43e (patch)
tree79aba07d072455e95ff3467b1e227ff7ee82b51b
parent18ae259cc4b60a670f4bf5cbd621bbe420c0c24b (diff)
Fix T43311: using displacement shader crashes blender
Issue was caused by wrong order of scene device update, which could lead to missing object flags in shader kernel. This patch solves a bit more than that making sure objects flags are always properly updated, so adding/removing volume BSDF will properly reflect on viewport where camera might become being in volume and so.
-rw-r--r--intern/cycles/render/mesh.cpp24
-rw-r--r--intern/cycles/render/mesh.h4
-rw-r--r--intern/cycles/render/object.cpp7
-rw-r--r--intern/cycles/render/object.h1
-rw-r--r--intern/cycles/render/scene.cpp9
-rw-r--r--intern/cycles/render/shader.cpp7
6 files changed, 43 insertions, 9 deletions
diff --git a/intern/cycles/render/mesh.cpp b/intern/cycles/render/mesh.cpp
index 815ecb310f4..9aa0cbcd06d 100644
--- a/intern/cycles/render/mesh.cpp
+++ b/intern/cycles/render/mesh.cpp
@@ -556,6 +556,7 @@ MeshManager::MeshManager()
{
bvh = NULL;
need_update = true;
+ need_flags_update = true;
}
MeshManager::~MeshManager()
@@ -1034,20 +1035,33 @@ void MeshManager::device_update_bvh(Device *device, DeviceScene *dscene, Scene *
dscene->data.bvh.use_qbvh = scene->params.use_qbvh;
}
+void MeshManager::device_update_flags(Device *device, DeviceScene *dscene, Scene *scene, Progress& progress)
+{
+ if(!need_update && !need_flags_update) {
+ return;
+ }
+ /* update flags */
+ foreach(Mesh *mesh, scene->meshes) {
+ mesh->has_volume = false;
+ foreach(uint shader, mesh->used_shaders) {
+ if(scene->shaders[shader]->has_volume) {
+ mesh->has_volume = true;
+ }
+ }
+ }
+ need_flags_update = false;
+}
+
void MeshManager::device_update(Device *device, DeviceScene *dscene, Scene *scene, Progress& progress)
{
if(!need_update)
return;
- /* update normals and flags */
+ /* update normals */
foreach(Mesh *mesh, scene->meshes) {
- mesh->has_volume = false;
foreach(uint shader, mesh->used_shaders) {
if(scene->shaders[shader]->need_update_attributes)
mesh->need_update = true;
- if(scene->shaders[shader]->has_volume) {
- mesh->has_volume = true;
- }
}
if(mesh->need_update) {
diff --git a/intern/cycles/render/mesh.h b/intern/cycles/render/mesh.h
index 90894564591..62e775e5bc9 100644
--- a/intern/cycles/render/mesh.h
+++ b/intern/cycles/render/mesh.h
@@ -79,7 +79,7 @@ public:
vector<uint> shader;
vector<bool> smooth;
- bool has_volume; /* Set in the device_update(). */
+ bool has_volume; /* Set in the device_update_flags(). */
vector<float4> curve_keys; /* co + radius */
vector<Curve> curves;
@@ -145,6 +145,7 @@ public:
BVH *bvh;
bool need_update;
+ bool need_flags_update;
MeshManager();
~MeshManager();
@@ -160,6 +161,7 @@ public:
void device_update_mesh(Device *device, DeviceScene *dscene, Scene *scene, Progress& progress);
void device_update_attributes(Device *device, DeviceScene *dscene, Scene *scene, Progress& progress);
void device_update_bvh(Device *device, DeviceScene *dscene, Scene *scene, Progress& progress);
+ void device_update_flags(Device *device, DeviceScene *dscene, Scene *scene, Progress& progress);
void device_free(Device *device, DeviceScene *dscene);
void tag_update(Scene *scene);
diff --git a/intern/cycles/render/object.cpp b/intern/cycles/render/object.cpp
index 87c45ceb151..1225125b57e 100644
--- a/intern/cycles/render/object.cpp
+++ b/intern/cycles/render/object.cpp
@@ -221,6 +221,7 @@ vector<float> Object::motion_times()
ObjectManager::ObjectManager()
{
need_update = true;
+ need_flags_update = true;
}
ObjectManager::~ObjectManager()
@@ -404,10 +405,11 @@ void ObjectManager::device_update(Device *device, DeviceScene *dscene, Scene *sc
void ObjectManager::device_update_flags(Device *device, DeviceScene *dscene,
Scene *scene, Progress& progress)
{
- if(!need_update)
+ if(!need_update && !need_flags_update)
return;
need_update = false;
+ need_flags_update = false;
if(scene->objects.size() == 0)
return;
@@ -427,6 +429,9 @@ void ObjectManager::device_update_flags(Device *device, DeviceScene *dscene,
if(object->mesh->has_volume) {
object_flag[object_index] |= SD_OBJECT_HAS_VOLUME;
}
+ else {
+ object_flag[object_index] &= ~SD_OBJECT_HAS_VOLUME;
+ }
foreach(Object *volume_object, volume_objects) {
if(object == volume_object) {
diff --git a/intern/cycles/render/object.h b/intern/cycles/render/object.h
index 574d44b6599..acc08a0e204 100644
--- a/intern/cycles/render/object.h
+++ b/intern/cycles/render/object.h
@@ -70,6 +70,7 @@ public:
class ObjectManager {
public:
bool need_update;
+ bool need_flags_update;
ObjectManager();
~ObjectManager();
diff --git a/intern/cycles/render/scene.cpp b/intern/cycles/render/scene.cpp
index ee7cef1950b..bb7c03cbe6d 100644
--- a/intern/cycles/render/scene.cpp
+++ b/intern/cycles/render/scene.cpp
@@ -170,8 +170,8 @@ void Scene::device_update(Device *device_, Progress& progress)
if(progress.get_cancel() || device->have_error()) return;
- progress.set_status("Updating Meshes");
- mesh_manager->device_update(device, &dscene, this, progress);
+ progress.set_status("Updating Meshes Flags");
+ mesh_manager->device_update_flags(device, &dscene, this, progress);
if(progress.get_cancel() || device->have_error()) return;
@@ -180,6 +180,11 @@ void Scene::device_update(Device *device_, Progress& progress)
if(progress.get_cancel() || device->have_error()) return;
+ progress.set_status("Updating Meshes");
+ mesh_manager->device_update(device, &dscene, this, progress);
+
+ if(progress.get_cancel() || device->have_error()) return;
+
progress.set_status("Updating Hair Systems");
curve_system_manager->device_update(device, &dscene, this, progress);
diff --git a/intern/cycles/render/shader.cpp b/intern/cycles/render/shader.cpp
index db7c93e5e5d..1fa949b17de 100644
--- a/intern/cycles/render/shader.cpp
+++ b/intern/cycles/render/shader.cpp
@@ -21,6 +21,7 @@
#include "light.h"
#include "mesh.h"
#include "nodes.h"
+#include "object.h"
#include "osl.h"
#include "scene.h"
#include "shader.h"
@@ -194,6 +195,7 @@ void Shader::tag_update(Scene *scene)
* e.g. surface attributes when there is only a volume shader. this could
* be more fine grained but it's better than nothing */
OutputNode *output = graph->output();
+ bool prev_has_volume = has_volume;
has_surface = has_surface || output->input("Surface")->link;
has_volume = has_volume || output->input("Volume")->link;
has_displacement = has_displacement || output->input("Displacement")->link;
@@ -215,6 +217,11 @@ void Shader::tag_update(Scene *scene)
need_update_attributes = true;
scene->mesh_manager->need_update = true;
}
+
+ if(has_volume != prev_has_volume) {
+ scene->mesh_manager->need_flags_update = true;
+ scene->object_manager->need_flags_update = true;
+ }
}
void Shader::tag_used(Scene *scene)