Threadsafe Spring System Query

Started by
4 comments, last by uutee 17 years, 11 months ago
Hi, I'm currently writing a spring based hair system. I've got all of the physics and hair generation code sorted, however it is evident that the performance would be boosted if I multi threaded the physics update step. At the moment my hair objects all update in a primary update function and are passed to a vertex buffer to be rendered in the primary update function. My question is:(This question relates primarily to win32) Is it enough to lock a shared resource buffer with a Critical Section in Thread A(Assuming thread A is the application primary thread or the DirectX thread) when the worker thread (the physics thread) could be updating the same buffer with newly calculated data from the physics step? If not, I would appreciate it if someone could offer me a pointer to what I should do? Thanks in advance, matt
Advertisement
What do you mean by improved performance? Unless you have multiple processors, or a multicore system, the physics update will not actually run faster with multithreading. In fact, it'll run slower. But, I agree that if you measure performance by the responsiveness of the app/game, then the user/player will perceive better performance with multithreading. And for games that is absolutely necessary.

If you are using dynamic vertex buffers, or vertex arrays, in main system RAM, then your approach with critical sections will work (e.g., each thread locks the critical section when it wants to use it, and the other thread blocks until the first thread is done). You may wish to be smart about it, if you have lots of objects, e.g., do not necessarily update every character's head-of-hair every frame. Stagger them so you don't end up blocking the main thread for long periods of time. If you are using static vertex buffers (silly for morphing geometry perhaps) in hardware, then obviously there is another step that has to happen---replacing the static hardware buffer. And, in that case, depending on your graphics API, the hardware update might have to happen in the main thread (to avoid threading issues with DirectX or OpenGL). And, so you'd have to have some event or messaging system to let the main thread know that indeed the buffer data has changed.....

Did that make any sense at all?
Graham Rhodes Moderator, Math & Physics forum @ gamedev.net
When multithreading an application, you should find a correct "granularity" of doing things. For example, giving half of the springs to processor 1 and the other half to processor 2 isn't very efficient since particles depend on each other through springs, so processors 1 and 2 require some kind of synchronization.

However, if you give half of the *hairs* to processor 1 and the other half to processor 2, you'll require no synchronization (if individual hairs are considered independent).

Unfortunately this disallows treating all hairs as a big collection of springs. One "generic" solution to MT problems is to aim for a more "functional" programming style, i.e instead of updating the "states" of the particles, you "map" the old particle set to a new particle set. If all processors use the old particle set in their update stage, everything works fine. The tradeoff is that updating the state might be faster than creating a completely new state (but mostly it's just the allocation overhead).

(Yes, there are way more solutions, especially if you can afford a little precomputation time, but no time to discuss everything here.)

-- Mikko
I'm not sure you can distribute the physics & mesh update to another processor without some synchronization. There is still the issue of rendering, and rendering likes to be done in a single thread due to the need to do GPU state management.
Graham Rhodes Moderator, Math & Physics forum @ gamedev.net
Thanks.

My development machine is an AMD X2 4600+. The second core will take care of physics if the machine that my demo runs on is dual core.

First off, thanks for the depth of discussion.

I feel I should expand a little first.

I'm attempting mimic the functionality in the mass spring model that Pixar used in "Monsters Inc".

Link

A short movie can be found at http://www.sensatefx.com/movies/hairtest.avi. The springs are not running in this release, however it will give you an idea of what I'm up to.

I've decided to do two tests.

1.) use libsh and attempt to move the computation to the video cards.
or
2.) continue with a second thread to update springs and transformation and render from a shared buffer. Also use the second thread to constrain update steps to 50 fps.

[Edited by - sensate on May 23, 2006 4:53:50 PM]
>>>I'm not sure you can distribute the physics & mesh update to another
>>>processor without some synchronization.

If two tasks are completely separate, they can be parallelized without locking. Of course a renderzvous, i.e waiting for all the threads to finish, is still required, but that doesn't slow down things like locking does.

>>>There is still the issue of rendering, and rendering likes to be
>>>done in a single thread due to the need to do GPU state management.

Personally I would just do the physics update and rendering completely sequentially, but so that when the physics update takes place, multiple processors are used.

With a functional approach it's possible to do physics and rendering simultaneously without locking: the physics engine maps the old state to new state, and graphics engine uses the old state to render a pretty picture.

You're right: rasterization-based rendering is not trivial to parallelize.

-- Mikko

This topic is closed to new replies.

Advertisement