private bool Update() { IMonitorModule monitorModule = RequestModuleInterface <IMonitorModule>(); ISimFrameMonitor simFrameMonitor = monitorModule.GetMonitor <ISimFrameMonitor>(this); ITotalFrameTimeMonitor totalFrameMonitor = monitorModule.GetMonitor <ITotalFrameTimeMonitor>(this); ILastFrameTimeMonitor lastFrameMonitor = monitorModule.GetMonitor <ILastFrameTimeMonitor>(this); IOtherFrameMonitor otherFrameMonitor = monitorModule.GetMonitor <IOtherFrameMonitor>(this); ISleepFrameMonitor sleepFrameMonitor = monitorModule.GetMonitor <ISleepFrameMonitor>(this); while (true) { if (!ShouldRunHeartbeat) //If we arn't supposed to be running, kill ourselves { return(false); } int maintc = Util.EnvironmentTickCount(); int BeginningFrameTime = maintc; // Increment the frame counter ++m_frame; try { int OtherFrameTime = Util.EnvironmentTickCount(); if (m_frame % m_update_coarse_locations == 0) { List <Vector3> coarseLocations; List <UUID> avatarUUIDs; if (SceneGraph.GetCoarseLocations(out coarseLocations, out avatarUUIDs, 60)) { // Send coarse locations to clients foreach (IScenePresence presence in GetScenePresences()) { presence.SendCoarseLocations(coarseLocations, avatarUUIDs); } } } if (m_frame % m_update_entities == 0) { m_sceneGraph.UpdateEntities(); } Action[] events; lock (m_events) { events = new Action[m_events.Count]; m_events.CopyTo(events); m_events.Clear(); } foreach (Action h in events) { try { h(); } catch { } } if (m_frame % m_update_events == 0) { m_sceneGraph.PhysicsScene.UpdatesLoop(); } if (m_frame % m_update_events == 0) { m_eventManager.TriggerOnFrame(); } //Now fix the sim stats int MonitorOtherFrameTime = Util.EnvironmentTickCountSubtract(OtherFrameTime); int MonitorLastCompletedFrame = Util.EnvironmentTickCount(); simFrameMonitor.AddFPS(1); lastFrameMonitor.SetValue(MonitorLastCompletedFrame); otherFrameMonitor.AddTime(MonitorOtherFrameTime); } catch (Exception e) { MainConsole.Instance.Error("[REGION]: Failed with exception " + e + " in region: " + RegionInfo.RegionName); return(true); } //Get the time between beginning and end maintc = Util.EnvironmentTickCountSubtract(BeginningFrameTime); //Beginning + (time between beginning and end) = end int MonitorEndFrameTime = BeginningFrameTime + maintc; int getSleepTime = GetHeartbeatSleepTime(maintc, false); if (getSleepTime > 0) { Thread.Sleep(getSleepTime); } if (sleepFrameMonitor != null) { sleepFrameMonitor.AddTime(maintc); totalFrameMonitor.AddFrameTime(MonitorEndFrameTime); } } }
void Heartbeat() { IMonitorModule monitorModule = RequestModuleInterface <IMonitorModule>(); ISimFrameMonitor simFrameMonitor = monitorModule.GetMonitor <ISimFrameMonitor>(this); ITotalFrameTimeMonitor totalFrameMonitor = monitorModule.GetMonitor <ITotalFrameTimeMonitor>(this); ILastFrameTimeMonitor lastFrameMonitor = monitorModule.GetMonitor <ILastFrameTimeMonitor>(this); IOtherFrameMonitor otherFrameMonitor = monitorModule.GetMonitor <IOtherFrameMonitor>(this); ISleepFrameMonitor sleepFrameMonitor = monitorModule.GetMonitor <ISleepFrameMonitor>(this); IPhysicsFrameMonitor physicsFrameMonitor = monitorModule.GetMonitor <IPhysicsFrameMonitor>(this); IPhysicsUpdateFrameMonitor physicsFrameTimeMonitor = monitorModule.GetMonitor <IPhysicsUpdateFrameMonitor>(this); IPhysicsMonitor physicsMonitor = RequestModuleInterface <IPhysicsMonitor>(); ILLClientInventory inventoryModule = RequestModuleInterface <ILLClientInventory>(); while (true) { if (!ShouldRunHeartbeat) //If we aren't supposed to be running, kill ourselves { return; } int maintc = Util.EnvironmentTickCount(); int BeginningFrameTime = maintc; // Increment the frame counter ++Frame; try { int OtherFrameTime = Util.EnvironmentTickCount(); ISceneEntity[] entities = null; lock (PhysicsReturns) { if (PhysicsReturns.Count != 0) { entities = PhysicsReturns.ToArray(); PhysicsReturns.Clear(); } } if (entities != null && inventoryModule != null) { inventoryModule.ReturnObjects(entities, UUID.Zero); } if (Frame % m_update_entities == 0) { m_sceneGraph.UpdateEntities(); } if (Frame % m_update_events == 0) { m_sceneGraph.PhysicsScene.UpdatesLoop(); } if (Frame % m_update_events == 0) { m_eventManager.TriggerOnFrame(); } if (Frame % m_update_coarse_locations == 0) { List <Vector3> coarseLocations; List <UUID> avatarUUIDs; if (SceneGraph.GetCoarseLocations(out coarseLocations, out avatarUUIDs, 60)) { // Send coarse locations to clients foreach (IScenePresence presence in GetScenePresences()) { presence.SendCoarseLocations(coarseLocations, avatarUUIDs); } } } int PhysicsUpdateTime = Util.EnvironmentTickCount(); if (Frame % m_update_physics == 0) { TimeSpan SinceLastFrame = DateTime.UtcNow - m_lastphysupdate; if (!RegionInfo.RegionSettings.DisablePhysics && ApproxEquals((float)SinceLastFrame.TotalMilliseconds, m_updatetimespan, 3)) { m_sceneGraph.UpdatePreparePhysics(); m_sceneGraph.UpdatePhysics((float)SinceLastFrame.TotalSeconds); m_lastphysupdate = DateTime.UtcNow; int MonitorPhysicsUpdateTime = Util.EnvironmentTickCountSubtract(PhysicsUpdateTime); if (MonitorPhysicsUpdateTime != 0) { if (physicsFrameTimeMonitor != null) { physicsFrameTimeMonitor.AddTime(MonitorPhysicsUpdateTime); } if (physicsMonitor != null) { physicsMonitor.AddPhysicsStats(RegionInfo.RegionID, PhysicsScene); } if (m_lastPhysicsChange != RegionInfo.RegionSettings.DisablePhysics) { StartPhysicsScene(); } } if (physicsFrameMonitor != null) { physicsFrameMonitor.AddFPS(1); } } else if (m_lastPhysicsChange != RegionInfo.RegionSettings.DisablePhysics) { StopPhysicsScene(); } m_lastPhysicsChange = RegionInfo.RegionSettings.DisablePhysics; } //Now fix the sim stats int MonitorOtherFrameTime = Util.EnvironmentTickCountSubtract(OtherFrameTime); int MonitorLastCompletedFrame = Util.EnvironmentTickCount(); simFrameMonitor.AddFPS(1); lastFrameMonitor.SetValue(MonitorLastCompletedFrame); otherFrameMonitor.AddTime(MonitorOtherFrameTime); } catch (Exception e) { MainConsole.Instance.Error("[Scene]: Failed with exception " + e + " in region: " + RegionInfo.RegionName); return; } //Get the time between beginning and end maintc = Util.EnvironmentTickCountSubtract(BeginningFrameTime); //Beginning + (time between beginning and end) = end int MonitorEndFrameTime = BeginningFrameTime + maintc; int getSleepTime = GetHeartbeatSleepTime(maintc); if (getSleepTime > 0) { Thread.Sleep(getSleepTime); } if (sleepFrameMonitor != null) { sleepFrameMonitor.AddTime(getSleepTime); totalFrameMonitor.AddFrameTime(MonitorEndFrameTime); } } }