Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

PushConstants causes ram usage to increase every command buffer #1118

Open
Owlkaline opened this issue Nov 24, 2018 · 8 comments
Open

PushConstants causes ram usage to increase every command buffer #1118

Owlkaline opened this issue Nov 24, 2018 · 8 comments

Comments

@Owlkaline
Copy link

Using a very slightly modified version of triangle example from latest repo (and vulkano 0.10.0 and 0.11.0). Cause ram usage to seemingly infinity increase ram usage.

By pushing a simple identity matrix into the vs shader as a pushconstant
Owlkaline@20c7fb0

This has happened on all computers i have been able to test (Both debug and release modes)
Ubuntu 18.10 GTX 950m Nvidia Driver 387.92 and 290.87
Ubuntu 18.10 GTX 770oc Nvidia Drive 390
Windows 10 AMD R280

It will fill the ram until system freezes/crashes from running out of ram (Tested up to 12GB).

That is if that my understanding on how to use push_constants should be used, that they are similar to uniform but are allocated every commandbuffer so is good for data that will change every frame such as a transformation matrix and that you are limited to (~128 bytes, approx 32 floats) but has much faster transfer rate than an ordinary uniform buffer.

Thus leading me to believe that the increase in ram usage is unintended.

The validation layers under release spam this output

Validation(ERROR): msg_code: 618662080: [ VUID-vkDestroyFence-fence-01120 ] Object: 0x1e (Type = 7) | Fence 0x1e is in use. The spec valid usage text states 'All queue submission commands that refer to fence must have completed execution' (https://www.khronos.org/registry/vulkan/specs/1.0/html/vkspec.html#VUID-vkDestroyFence-fence-01120)

@Owlkaline Owlkaline changed the title PushConstants causes ram usage to increase every drawcall PushConstants causes ram usage to increase every command buffer Nov 24, 2018
@rukai
Copy link
Member

rukai commented Nov 25, 2018

I cant reproduce on Linux + Nvidia GTX 960, Linux + AMD or Windows + AMD.
I left it for at least 5 minutes on all and didnt notice an increase in memory usage.
How long does it take to OoM?

Could you possibly be encountering #923 ?
The work around for that, which you could try is adding future.wait(None).unwrap like this https://github.com/rukai/incipisphere_renderer/blob/d8c06451e8dc1c4b63ea4c7fdf682270d16f4cbd/src/render.rs#L309

@Owlkaline
Copy link
Author

Owlkaline commented Nov 25, 2018

tldr: future.wait(None).unwrap() with push constants enhances the issues with push_constants

I thought "future.wait(None).unwrap()" was in examples by default for some reason xD

I first experienced this in my own project, which does incorporate future.wait(None).unwrap() work around, as i needed it long time ago vulkano 0.7.0 or something.

Once i remove the push constants it stops leaking (in my project).
The rate of the leak is a connected to how many frames you are rendering per second.

Ok so far trial and error with triangle and project it seems the combination of

  • Using Push Constants
  • Having future.wait(None).unwrap()

On both tests (push constants with future.wait and just push constants) ram usage starts at approximately 20.3mb

Push Constants + future.wait(None).unwrap()

Causes it to leak substantially (5gb in 4min, 20mb/s)
https://user-images.githubusercontent.com/11486093/48981153-b7839680-f11d-11e8-95e1-e75128265103.png

As can be seen after approximately 4min it was still running and had taken up 4GB of ram memory.

Push Constants

However without the future.wait(None).unwrap()
It does still leak just so much slower here it memory after 4min also (30mb in 4min, 0.12mb/s)
https://user-images.githubusercontent.com/11486093/48981210-5a3c1500-f11e-11e8-830d-d6f9350a72cf.png
with the version without future.wait(None).unwrap() it seems to take a variable amount of time before it starts leaking, sometimes it as soon as its run, other times after 30seconds, another run was after 5 seconds.

Another note when i had a look at the memory maps, there was a singular anonymous mapped region that had a VM size of 6gb.

Don't have access to other computers to test currently.

Edit: Same across PresentModes Immediate, Fifo and Relaxed (Mailbox not supported) so i don't think its related directly to #923
And I haven't seen and kind of Oom errors. other than pc coming to standstill once all ram is used
--release mode is where the leak happens consistently without fail

Edit 2: I just tested on my desktop with fresh install of Ubuntu 18.10 GTX 770, I didn't see any leak with push constants alone with the modified triangle, but when it was run with future.wait(None).unwrap() the issue was present.

@rukai
Copy link
Member

rukai commented Nov 25, 2018

I was testing with future.wait(None).unwrap() before and couldn't reproduce it.

@Owlkaline
Copy link
Author

Owlkaline commented Nov 26, 2018

After further testing, and thought

I do believe it is part of issue #923 but because my laptop has the Nvidia optimus technology that forces Nvidia to go through the Intel gpu, vulkan believes its using the INTEL-MESA driver, but then picks the GTX770 card for vulkan rendering (only one available with the optimus workaround), so that the memory checks don't apply correctly, thus leading no Oom errors etc.
With the main difference being that is still leaks on Immediate mode, but im going to chalk that up to the optimus driver issue.

Output at launch:

INTEL-MESA: warning: Haswell Vulkan support is incomplete
Using device: GeForce GTX 950M (type: DiscreteGpu)

future.wait(None).unwrap(), does fix the issue when no pushconstants are used.
But for some reason using push constants breaks the future fix.

Although I do still get a memory leak on my desktop when using both (future.wait(None).unwrap() + PushConstants), where it just uses the standard Nvidia setup provided by Ubuntu 18.10.

I can test later tonight if removing future.wait(None).unwrap(), with the push constants on my desktop still causes the leak.

@kgnlp
Copy link

kgnlp commented Jan 9, 2021

I'm also running into host memory leaks (~1mb/s) on my GTX 1070 (notably no Optimus) using only a storage CpuAccessibleBuffer, an ImmutableImage and push constants. Valgrind reports memory allocated via push constants as definitely lost:

==70200== 1,015,036 bytes in 187 blocks are definitely lost in loss record 1,455 of 1,455
==70200==    at 0x483CB65: calloc (vg_replace_malloc.c:760)
==70200==    by 0x633A043: ??? (in /usr/lib/libnvidia-glcore.so.460.32.03)
==70200==    by 0x66CC961: ??? (in /usr/lib/libnvidia-glcore.so.460.32.03)
==70200==    by 0x66F1433: ??? (in /usr/lib/libnvidia-glcore.so.460.32.03)
==70200==    by 0x42423C: vk_sys::DevicePointers::CmdPushConstants (lib.rs:2848)
==70200==    by 0x41F0EA: vulkano::command_buffer::sys::UnsafeCommandBufferBuilder<P>::push_constants (sys.rs:1316)
==70200==    by 0x2F0EB7: <vulkano::command_buffer::synced::commands::<impl vulkano::command_buffer::synced::base::SyncCommandBufferBuilder<P>>::push_constants::Cmd<Pl> as vulkano::command_buffer::synced::base::Command<P>>::send (commands.rs:1735)
==70200==    by 0x28835D: vulkano::command_buffer::synced::base::SyncCommandBufferBuilder<P>::build (base.rs:760)
==70200==    by 0x3B0E6E: vulkano::command_buffer::auto::AutoCommandBufferBuilder<P>::build (auto.rs:575)

Using future.wait(None).unwrap() only causes memory to leak more slowly and doesn't seem to fix underlying issues as far as I can tell. Present modes also don't make a difference.

Edit: I replaced the push constants with () and used a CpuBufferPool instead and there are no more leaks. I can also now confirm that push constant leaks do not occur when running on an integrated Intel HD chip

@kgnlp
Copy link

kgnlp commented Jan 10, 2021

I also found that the pushconstants examples from this repository doesn't leak on my machine

@lictex
Copy link

lictex commented Feb 11, 2021

also running into this issue on windows 10 with nvidia rtx 2070 mobile. (intel gpu doesnt leak tho)
this will happen when i add a push constant into triangle example's vertex shader, no matter what i passed to draw().

i tried to play with runtime-shader example with the push constant added into vertex shader same as above and got some results

not sure whether this is a nvidia driver bug but i think we need some workarounds as currently push constants is just unusable..


edit: confirmed changing this solved the issue on triangle example for me, but then compute shaders are just broken...

stages: ShaderStages::all(), // FIXME: wrong

@trevex
Copy link
Contributor

trevex commented Dec 10, 2022

Tried to reproduce on Windows 10 with NV 1080 Ti (driver 527.56), added push constants as illustrated by Owlkaline@20c7fb0 (using 10d7349) , but can not observe a memory leak.

@Rua Rua added the type: bug label Aug 14, 2023
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

No branches or pull requests

6 participants