🎉 Celebrating 25 Years of GameDev.net! 🎉

Not many can claim 25 years on the Internet! Join us in celebrating this milestone. Learn more about our history, and thank you for being a part of our community!

[D3D12] Ring buffer corruption

Started by
6 comments, last by JGP 1 year, 4 months ago

Hi!

I am using one single upload heap (several megabytes) to allocate the draw data (constant buffers) of my draw calls. This is mapped once and reused for all the frames.

The approach used is a simple buffer with a tail pointer (which starts at the mapped virtual GPU address of the heap) and which is offseted as the system requires to allocate more memory.

Everything seems to work fine except when the buffer is full (there is no more space to allocate memory). So the approach here is to set the tail pointer to the beginning of the heap again to start filling it out from the very beginning. This is happening once every ~100 frames, so there is no chance to write memory which is still being used by the GPU to render stuff.

After this point, the constant buffers (according to PIX and to the visuals being corrupted) seem corrupted, which I don't understand because I am jsut overwriting the old data which is no longer being used.

Anything obvious that I am missing?

Thanks for helping!

Advertisement

Are you sure you are using the correct alignment?

Yes, I am aligning to 256 bytes and everything seems to work properly until I start writting to the heap from the beginning, in which case things in that buffer seem to corrupt for some reason…

I actually have one buffer per frame slot. However, I believe you are a supposed to be able to use a single one as long as you aren't writing some to place the GPU is using. It's hard to say without going into the code. I mean it could be a simple bug. If you get desperate, I guess you could try splitting your buffer so there is one per frame, but you're right in that you shouldn't need to, and I think Frank Luna does it that way in his book.

I see. What is the advantage to using multiple buffers (one per frame slot?) compared to this approach? Isn't it simpler to use just one buffer?

For me it's an organizational thing. I have “frame slots” in my engine. I asked the same question you just asked once, and I didn't get a definitive answer, so I just picked a solution. The other thing is I'm not using a ring-buffer. I start from the beginning each frame. If the data exceeds the space in the buffer, I resize it.

I'm not saying you should necessarily do it this way. It's just what I do, and it works for me. I tend to be conservative if something seems iffy to me.

The other thing is constant buffers can be part of my “material” definitions. That's because I do a lot of procedural textures and they often require specialized data. So it's part of my API. I find everyone has vastly different use cases when using DX12 because it's very low level.

Nice thanks for the info!

This topic is closed to new replies.

Advertisement