t3kt / raytk

Raymarching shader toolkit for TouchDesigner
https://raytk.net
Other
236 stars 15 forks source link

High memory usage / Unresponsive touchdesigner on shader build #569

Open edeetee opened 3 years ago

edeetee commented 3 years ago

When making a change to my raytk network, my memory climbs as high as 10GB. This memory goes up and down (garbage collection probably) for a few minutes before TD returns from being unresponsive.

Some solutions that would help:

edeetee commented 3 years ago

If someone has an idea what the best course of action is, I could have a go trying to remedy it - already tried making some changes to the source.

t3kt commented 3 years ago

The memory issue is not something that I've encountered before. Could you upload a project that demonstrates the issue? It would also be useful to know:

There is going to be lag when the GPU driver compiles the shader. That happens any time something causes the generated code to change. As far as I am aware, GPU drivers do not provide a way to compile parts of the shader for reuse. We don't really have any control over that process, without being able to modify the internals of TouchDesigner or creating a replacement for the GLSL TOP. If you know of any alternatives, that would be really useful.

The more complex the generated shader, the longer it takes to compile. There are some operators that involve a lot of additional code (like waveletNoiseField), so avoiding those would help reduce the time.

Things that typically cause recompiles:

The best approach is to avoid making those kinds of changes in the network while in situations where stalling would be problematic (e.g. live performance, recording output, etc). If you're switching between parts of the network, you can use a Switch ROP, which lets you switch operators without requiring a recompile. Menu parameters can be a bit harder to avoid. In certain cases it may be possible to redesign them to use runtime-based evaluation. But in other cases the settings in one operator result in changes to the behavior of other operators throughout the network.

edeetee commented 3 years ago

Here is pretty much all I have with raytk at the moment. For me, any network change causes 1+ minutes of unresponsive program. The network is composed of a couple of texture manipulation things for UV inputs and for calculating a normalized distance for some color effects. The rest is shaping and materials. slowShaderCompileTest.zip

RAM: 16GB CPU: Intel(R) Core(TM) i7-8750H CPU @ 2.20GHz 2.21 GHz GPU: RTX 2070 MaxQ (Laptop)

edeetee commented 3 years ago

Through trail and error, It seems like the generalised geodesic sdfs are causing some of the build freezing. Investigating more

t3kt commented 3 years ago

First of all, the result looks amazing.

I am able to reproduce the stalling issue. When I was saying some stalling is to be expected, it's generally in the range of a few seconds. So this is definitely outside the norm.

This is by far the most complex RayTK network I've ever seen. Some stats:

For comparison, one of my most complex scenes uses 20 operators.

As a sort-of workaround, while making changes to the network, you could disable cooking on the renderer, which should stop it from recompiling for each change.

But more importantly, there are some ways you can change your network design to improve performance (both runtime and compile). Things that are good practices for TouchDesigner in general don't always work well with the toolkit.

There is a cost for every ROP in the network. While that's technically true for everything in TD (except nulls), there's an advanced system of dependency evaluation that means that only things that are being used have much runtime cost. In RayTK, an entire render graph is compiled into a shader and run in a single TOP.

Some suggestions:

The reasons for these things are complicated, but if you're interested I'd be happy to discuss it and see if you have any ideas on how to improve things.

edeetee commented 3 years ago

Thanks for the compliment. I think you've build an impressive library here too :)

The reason the network is so large is that I was doing my own sdf data generation (depth, position, mat type), then doing all of the material processing in tops. This gave me pretty shoddy performance, I'm guessing due to how TOPS use textures instead of optimising into a shader. I came across your library and decided to see if I would get performance improvements. I definitely got performance improvements but now I'm getting these problems.

The most utility I get from your library is:

I think it's getting to the point of complexity where using a shader building library may be helpful. I can write shader code that reuses inputs in the right context so there must be some way to generate it. Probably more type info tracking or something to decide wether or not a value can be reused.

I think from here I'll try reduce my field usage and see if my assumption of reusing input operators allows me to simplify other things.