From 5976ac16b0eedaeca2360010a3d6f7be4213700a Mon Sep 17 00:00:00 2001 From: Dan Lake Date: Tue, 13 Oct 2009 19:13:06 -0700 Subject: Optimized heartbeat by calling Update() only on updated objects. During the heartbeat loop, Update() is called on every SceneObjectGroup which in turn checks if any SceneObjectPart has changed. For large regions (> 100k prims) this work consumes 20-30% of a CPU even though there are only a few objects updating each frame. There is only one other reason to check every object on every frame, and that is the case where a script has registered the object with an "at target" listener. We can easily track when an object is registered or unregistered with an AtTarget, so this is not a reason to check every object every heartbeat. In the attached patch, I have added a dictionary to the scene which tracks the objects which have At Targets. Each heartbeat, the AtTarget() function will be called on every object registered with a listener for that event. Also, I added a dictionary to SceneGraph which stores references to objects which have been queued for updates during the heartbeat. At each heartbeat, Update() is called only on the objects which have generated updates during that beat. --- OpenSim/Region/Framework/Scenes/SceneGraph.cs | 28 +++++++++------------------ 1 file changed, 9 insertions(+), 19 deletions(-) (limited to 'OpenSim/Region/Framework/Scenes/SceneGraph.cs') diff --git a/OpenSim/Region/Framework/Scenes/SceneGraph.cs b/OpenSim/Region/Framework/Scenes/SceneGraph.cs index 54ac792..9cd2247 100644 --- a/OpenSim/Region/Framework/Scenes/SceneGraph.cs +++ b/OpenSim/Region/Framework/Scenes/SceneGraph.cs @@ -77,7 +77,7 @@ namespace OpenSim.Region.Framework.Scenes protected RegionInfo m_regInfo; protected Scene m_parentScene; - protected Dictionary m_updateList = new Dictionary(); + protected Dictionary m_updateList = new Dictionary(); protected int m_numRootAgents = 0; protected int m_numPrim = 0; protected int m_numChildAgents = 0; @@ -155,16 +155,6 @@ namespace OpenSim.Region.Framework.Scenes } } - protected internal void UpdateEntities() - { - List updateEntities = GetEntities(); - - foreach (EntityBase entity in updateEntities) - { - entity.Update(); - } - } - protected internal void UpdatePresences() { List updateScenePresences = GetScenePresences(); @@ -365,12 +355,12 @@ namespace OpenSim.Region.Framework.Scenes } /// - /// Add an entity to the list of prims to process on the next update + /// Add an object to the list of prims to process on the next update /// /// - /// A + /// A /// - protected internal void AddToUpdateList(EntityBase obj) + protected internal void AddToUpdateList(SceneObjectGroup obj) { lock (m_updateList) { @@ -381,18 +371,18 @@ namespace OpenSim.Region.Framework.Scenes /// /// Process all pending updates /// - protected internal void ProcessUpdates() + protected internal void UpdateObjectGroups() { - Dictionary updates; + Dictionary updates; // Some updates add more updates to the updateList. // Get the current list of updates and clear the list before iterating lock (m_updateList) { - updates = new Dictionary(m_updateList); + updates = new Dictionary(m_updateList); m_updateList.Clear(); } - // Go through all timers - foreach (KeyValuePair kvp in updates) + // Go through all updates + foreach (KeyValuePair kvp in updates) { // Don't abort the whole update if one entity happens to give us an exception. try -- cgit v1.1