Sign in to follow this  
CommanderXXL

Managing Game Interface Pointers

Recommended Posts

Hi, i have a really tough problem in my Game Design: My Engine is based upon a server like master class called CComServer. Ths is the Main module which loads at startup. All other modules are in separate DLL files, one for each interface i need, so there are: Renderer (2 different of these), Sound (2 different), logic (this is the complete game logic which controls the actors, or when there is a video to play), WorldManager (this module uses another style of dlls which locate loaders for different world formats like quake3, doom3 and so on.) and input (based upon direct input) there are more but these are most important ones. Each of these Modules is derived from a class called CComClient. Each "Client" registers itself at the ComServer at startup and logs itself out of it when the dll ist unloaded (At Game End mostly). There is no given startup sequence for this modules. They load all at the same time with multiple threads for doing so. Now my Problem is the following: Some modules depend on others, for example the input interface can do nothing without a window from which to get the input an this is handled by the renderer interface. I used to have a method in my ComServer from which i could get the Interface Pointer to a module. But now i want these modules to be able to dynamically load or unload during runtime (to switch renderer from direct3d to opengl for example) this would require that all modules which depend on this switched module would get some sort of notify that their dependent module is no longer available and later upon the completition of loading the replacment module get another notification that now there is a new module which needs all setup work needed to be done again by the using module. I have now implemented a class which is some sort of smart pointer to the interfaces. This class is able to maintain the pointer to the interface. It gets set to Null when a module is unloaded and it gets the new pointer when the new module is loaded again. So far so good. But now i want this "Notification" thing so that the module which holds such a "smart pointer" is able to know when it can go to sleep and when it needs to setup its required modules again. Do you have any good suggestions on how i can accomplish this so that it is well integrated in the given environment? Thanks for reading this long post and more thanks for giving me a good advice *g*

Share this post


Link to post
Share on other sites
Hmm, this is a bit beyond me, and I'm afraid I can't really offer any sort of code examples or anything.

Perhaps I missed something (or the whole point), but could you perhaps have each module store a copy of each pointer when they are loaded, and then each 'cycle' (whatever that may be in each module, probably message based?), check the current pointer against it? Would almost certainly lead to desynchronization though.

You may be able to have each module simply ask the server for a current pointer each 'cycle', but that may (almost certainly) be performance hindering.

Perhaps the best solution I can think of may be that you could just do it with messages? Do you have a system set up so that the modules can communicate with each other in any way aside from variables? Perhaps the best solution would be to have whatever module keeps up with the others to issue a message when a module needs to be unloaded, and when it is reloaded, issue a new pointer? Wouldn't this be handled by the 'server'?

You did say you had a 'smart pointer' set up, as a class. Perhaps you could have that use a messaging system instead of the server? Would possibly cut down on the overhead of the whole idea. Whenever the pointer detects a change it could just send a notification to the relevant modules.

Again, like I said I don't know much about the specifics of such an implementation, but keeping it simple has always worked for me, and a simple message system seems like the simplest way to go.

Sorry I can't be of more help.

Share this post


Link to post
Share on other sites
If all you want is for the pointers to get updated in the dependent modules, then you can just add an extra indirection and have your smart pointer objects store a CComClient** instead of a CComClient*. That way, when you change module, you only have one pointer to worry about, and all the smart pointers automatically get retargeted.

If you want the reloading of a given module to trigger the reinitialization of all the modules that depended on it, you have quite a bit more work to do. For starters, each module needs to keep track of what modules depend on itself (that should be a directed, acyclic graph). Second, if you want each dependent module to only be reinitialized once (if A depends on B and C, B depends on C, and C gets reloaded, you only want A to be reinitialized once, and that only after B has) you will have to keep a data structure that lets you traverse that graph in topological order (search for 'topological sort').

Beyond that, a lot depends (pun unintended) on how much of the process you want to be automated, on whether it should tie into garbage collection/reference counting, etc...

One thing is certain: a graph library (e.g. boost::graph) will probably help a lot.

Share this post


Link to post
Share on other sites
Thanks for your quick answers. I got the idea of both your suggestions and i think i will implement a mix of both. I have indeed a message system basend on my CComServer online and the server is able to track the graph with all dependecies of the modules as it gets notified when a module starts and quits. And when such a module is registering one of it's smart pointers there is always the owner of this pointer stored in it and therefore the server knows which module depends on which others.

I think i'll try using some sort of callback mechanism which gets called by the smart pointers in the owner module, which will then trigger the commands required when loading a new module.

Share this post


Link to post
Share on other sites

Create an account or sign in to comment

You need to be a member in order to leave a comment

Create an account

Sign up for a new account in our community. It's easy!

Register a new account

Sign in

Already have an account? Sign in here.

Sign In Now

Sign in to follow this