[Bf-committers] [Bf-blender-cvs] SVN commit: /data/svn/bf-blender [56650] trunk/blender/intern/cycles/render : Fix #35272: cycles GPU crash with anisotropic shader in group node.

Brecht Van Lommel brechtvanlommel at pandora.be
Fri May 10 17:11:23 CEST 2013


Thanks for pointing out, was simple mistake, fixed now.

On Fri, May 10, 2013 at 4:38 PM, Lukas Tönne <lukas.toenne at gmail.com> wrote:
> Hmm, i think this broke nested node groups :/
>
> I'm getting warnings again: "Cycles shader graph: detected cycle in graph,
> connection removed."
> Here's a little test file, contains a bunch of nested vector math
> functions, just start render: http://www.pasteall.org/blend/21270
>
> Works correctly in 56649. I can have a look myself tomorrow if necessary.
>
>
> On Fri, May 10, 2013 at 1:31 PM, Brecht Van Lommel <
> brechtvanlommel at pandora.be> wrote:
>
>> Revision: 56650
>>
>> http://projects.blender.org/scm/viewvc.php?view=rev&root=bf-blender&revision=56650
>> Author:   blendix
>> Date:     2013-05-10 11:31:57 +0000 (Fri, 10 May 2013)
>> Log Message:
>> -----------
>> Fix #35272: cycles GPU crash with anisotropic shader in group node.
>>
>> Problem was that due to group proxy node the anisotropic node did not
>> detect
>> early enough that it needs generated texture coordinate data to generate
>> the
>> tangent. Now the proxy nodes are removed earlier.
>>
>> Modified Paths:
>> --------------
>>     trunk/blender/intern/cycles/render/graph.cpp
>>     trunk/blender/intern/cycles/render/graph.h
>>     trunk/blender/intern/cycles/render/shader.cpp
>>
>> Modified: trunk/blender/intern/cycles/render/graph.cpp
>> ===================================================================
>> --- trunk/blender/intern/cycles/render/graph.cpp        2013-05-10
>> 10:07:01 UTC (rev 56649)
>> +++ trunk/blender/intern/cycles/render/graph.cpp        2013-05-10
>> 11:31:57 UTC (rev 56650)
>> @@ -312,10 +312,14 @@
>>         }
>>  }
>>
>> -void ShaderGraph::remove_proxy_nodes(vector<bool>& removed)
>> +void ShaderGraph::remove_unneeded_nodes()
>>  {
>> +       vector<bool> removed(nodes.size(), false);
>> +       bool any_node_removed = false;
>> +
>> +       /* find and unlink proxy nodes */
>>         foreach(ShaderNode *node, nodes) {
>> -               if (node->special_type == SHADER_SPECIAL_TYPE_PROXY) {
>> +               if(node->special_type == SHADER_SPECIAL_TYPE_PROXY) {
>>                         ProxyNode *proxy = static_cast<ProxyNode*>(node);
>>                         ShaderInput *input = proxy->inputs[0];
>>                         ShaderOutput *output = proxy->outputs[0];
>> @@ -327,7 +331,7 @@
>>                         ShaderOutput *from = input->link;
>>
>>                         /* bypass the proxy node */
>> -                       if (from) {
>> +                       if(from) {
>>                                 disconnect(input);
>>                                 foreach(ShaderInput *to, links) {
>>                                         disconnect(to);
>> @@ -345,6 +349,7 @@
>>                         }
>>
>>                         removed[proxy->id] = true;
>> +                       any_node_removed = true;
>>                 }
>>
>>                 /* remove useless mix closures nodes */
>> @@ -360,7 +365,7 @@
>>
>>                                 foreach(ShaderInput *input, inputs) {
>>                                         disconnect(input);
>> -                                       if (output)
>> +                                       if(output)
>>                                                 connect(output, input);
>>                                 }
>>                         }
>> @@ -378,33 +383,47 @@
>>                                         vector<ShaderInput*> inputs =
>> mix->outputs[0]->links;
>>
>>                                         foreach(ShaderInput *sock,
>> mix->inputs)
>> -                                       if(sock->link)
>> -                                               disconnect(sock);
>> +                                               if(sock->link)
>> +                                                       disconnect(sock);
>>
>>                                         foreach(ShaderInput *input,
>> inputs) {
>>                                                 disconnect(input);
>> -                                               if (output)
>> -                                               connect(output, input);
>> +                                               if(output)
>> +                                                       connect(output,
>> input);
>>                                         }
>>                                 }
>>                                 /* Factor 1.0 */
>> -                               else if (mix->inputs[0]->value.x == 1.0f) {
>> +                               else if(mix->inputs[0]->value.x == 1.0f) {
>>                                         ShaderOutput *output =
>> mix->inputs[2]->link;
>>                                         vector<ShaderInput*> inputs =
>> mix->outputs[0]->links;
>>
>>                                         foreach(ShaderInput *sock,
>> mix->inputs)
>> -                                       if(sock->link)
>> -                                               disconnect(sock);
>> +                                               if(sock->link)
>> +                                                       disconnect(sock);
>>
>>                                         foreach(ShaderInput *input,
>> inputs) {
>>                                                 disconnect(input);
>> -                                               if (output)
>> +                                               if(output)
>>                                                         connect(output,
>> input);
>>                                         }
>>                                 }
>>                         }
>>                 }
>>         }
>> +
>> +       /* remove nodes */
>> +       if (any_node_removed) {
>> +               list<ShaderNode*> newnodes;
>> +
>> +               foreach(ShaderNode *node, nodes) {
>> +                       if(!removed[node->id])
>> +                               newnodes.push_back(node);
>> +                       else
>> +                               delete node;
>> +               }
>> +
>> +               nodes = newnodes;
>> +       }
>>  }
>>
>>  void ShaderGraph::break_cycles(ShaderNode *node, vector<bool>& visited,
>> vector<bool>& on_stack)
>> @@ -433,27 +452,17 @@
>>
>>  void ShaderGraph::clean()
>>  {
>> +       /* remove proxy and unnecessary mix nodes */
>> +       remove_unneeded_nodes();
>> +
>>         /* we do two things here: find cycles and break them, and remove
>> unused
>>          * nodes that don't feed into the output. how cycles are broken is
>>          * undefined, they are invalid input, the important thing is to
>> not crash */
>>
>> -       vector<bool> removed(nodes.size(), false);
>>         vector<bool> visited(nodes.size(), false);
>>         vector<bool> on_stack(nodes.size(), false);
>>
>>         list<ShaderNode*> newnodes;
>> -
>> -       /* remove proxy nodes */
>> -       remove_proxy_nodes(removed);
>> -
>> -       foreach(ShaderNode *node, nodes) {
>> -               if(!removed[node->id])
>> -                       newnodes.push_back(node);
>> -               else
>> -                       delete node;
>> -       }
>> -       nodes = newnodes;
>> -       newnodes.clear();
>>
>>         /* break cycles */
>>         break_cycles(output(), visited, on_stack);
>> @@ -464,7 +473,7 @@
>>                         foreach(ShaderInput *to, node->inputs) {
>>                                 ShaderOutput *from = to->link;
>>
>> -                               if (from) {
>> +                               if(from) {
>>                                         to->link = NULL;
>>
>> from->links.erase(remove(from->links.begin(), from->links.end(), to),
>> from->links.end());
>>                                 }
>>
>> Modified: trunk/blender/intern/cycles/render/graph.h
>> ===================================================================
>> --- trunk/blender/intern/cycles/render/graph.h  2013-05-10 10:07:01 UTC
>> (rev 56649)
>> +++ trunk/blender/intern/cycles/render/graph.h  2013-05-10 11:31:57 UTC
>> (rev 56650)
>> @@ -239,6 +239,7 @@
>>         void connect(ShaderOutput *from, ShaderInput *to);
>>         void disconnect(ShaderInput *to);
>>
>> +       void remove_unneeded_nodes();
>>         void finalize(bool do_bump = false, bool do_osl = false, bool
>> do_multi_closure = false);
>>
>>  protected:
>> @@ -247,7 +248,6 @@
>>         void find_dependencies(set<ShaderNode*>& dependencies, ShaderInput
>> *input);
>>         void copy_nodes(set<ShaderNode*>& nodes, map<ShaderNode*,
>> ShaderNode*>& nnodemap);
>>
>> -       void remove_proxy_nodes(vector<bool>& removed);
>>         void break_cycles(ShaderNode *node, vector<bool>& visited,
>> vector<bool>& on_stack);
>>         void clean();
>>         void bump_from_displacement();
>>
>> Modified: trunk/blender/intern/cycles/render/shader.cpp
>> ===================================================================
>> --- trunk/blender/intern/cycles/render/shader.cpp       2013-05-10
>> 10:07:01 UTC (rev 56649)
>> +++ trunk/blender/intern/cycles/render/shader.cpp       2013-05-10
>> 11:31:57 UTC (rev 56650)
>> @@ -66,6 +66,12 @@
>>
>>  void Shader::set_graph(ShaderGraph *graph_)
>>  {
>> +       /* do this here already so that we can detect if mesh or object
>> attributes
>> +        * are needed, since the node attribute callbacks check if their
>> sockets
>> +        * are connected but proxy nodes should not count */
>> +       if(graph_)
>> +               graph_->remove_unneeded_nodes();
>> +
>>         /* assign graph */
>>         delete graph;
>>         delete graph_bump;
>>
>> _______________________________________________
>> Bf-blender-cvs mailing list
>> Bf-blender-cvs at blender.org
>> http://lists.blender.org/mailman/listinfo/bf-blender-cvs
>>
> _______________________________________________
> Bf-committers mailing list
> Bf-committers at blender.org
> http://lists.blender.org/mailman/listinfo/bf-committers


More information about the Bf-committers mailing list