diff options
author | Justin Clark-Casey (justincc) | 2014-09-26 20:05:22 +0100 |
---|---|---|
committer | Justin Clark-Casey (justincc) | 2014-11-25 23:18:38 +0000 |
commit | 7bababaab64ccac7153f68c19a3988764d537b1e (patch) | |
tree | 3ed7b2db238fd605a2673aef2bdad57376705888 /OpenSim/Region | |
parent | Make BulletSim thread be ThreadPriority.Highest if running (diff) | |
download | opensim-SC-7bababaab64ccac7153f68c19a3988764d537b1e.zip opensim-SC-7bababaab64ccac7153f68c19a3988764d537b1e.tar.gz opensim-SC-7bababaab64ccac7153f68c19a3988764d537b1e.tar.bz2 opensim-SC-7bababaab64ccac7153f68c19a3988764d537b1e.tar.xz |
Improve frame time stability by taking a few unnecessary repeated calculations out of the main scene loop.
Also uses a wait event to sleep rather than a Thread.Sleep to allow the loop to be interrupted in a more controlled manner when necessary.
Diffstat (limited to 'OpenSim/Region')
-rw-r--r-- | OpenSim/Region/Framework/Scenes/Scene.cs | 59 | ||||
-rw-r--r-- | OpenSim/Region/Framework/Scenes/SimStatsReporter.cs | 4 |
2 files changed, 42 insertions, 21 deletions
diff --git a/OpenSim/Region/Framework/Scenes/Scene.cs b/OpenSim/Region/Framework/Scenes/Scene.cs index ce048ef..2da254b 100644 --- a/OpenSim/Region/Framework/Scenes/Scene.cs +++ b/OpenSim/Region/Framework/Scenes/Scene.cs | |||
@@ -360,14 +360,31 @@ namespace OpenSim.Region.Framework.Scenes | |||
360 | public uint MaintenanceRun { get; private set; } | 360 | public uint MaintenanceRun { get; private set; } |
361 | 361 | ||
362 | /// <summary> | 362 | /// <summary> |
363 | /// The minimum length of time in seconds that will be taken for a scene frame. If the frame takes less time then we | 363 | /// The minimum length of time in milliseconds that will be taken for a scene frame. If the frame takes less time then we |
364 | /// will sleep for the remaining period. | 364 | /// will sleep for the remaining period. |
365 | /// </summary> | 365 | /// </summary> |
366 | /// <remarks> | 366 | /// <remarks> |
367 | /// One can tweak this number to experiment. One current effect of reducing it is to make avatar animations | 367 | /// One can tweak this number to experiment. One current effect of reducing it is to make avatar animations |
368 | /// occur too quickly (viewer 1) or with even more slide (viewer 2). | 368 | /// occur too quickly (viewer 1) or with even more slide (viewer 2). |
369 | /// </remarks> | 369 | /// </remarks> |
370 | public float MinFrameTime { get; private set; } | 370 | public int MinFrameTicks |
371 | { | ||
372 | get { return m_minFrameTicks; } | ||
373 | private set | ||
374 | { | ||
375 | m_minFrameTicks = value; | ||
376 | MinFrameSeconds = (float)m_minFrameTicks / 1000; | ||
377 | } | ||
378 | } | ||
379 | private int m_minFrameTicks; | ||
380 | |||
381 | /// <summary> | ||
382 | /// The minimum length of time in seconds that will be taken for a scene frame. | ||
383 | /// </summary> | ||
384 | /// <remarks> | ||
385 | /// Always derived from MinFrameTicks. | ||
386 | /// </remarks> | ||
387 | public float MinFrameSeconds { get; private set; } | ||
371 | 388 | ||
372 | /// <summary> | 389 | /// <summary> |
373 | /// The minimum length of time in seconds that will be taken for a maintenance run. | 390 | /// The minimum length of time in seconds that will be taken for a maintenance run. |
@@ -412,8 +429,11 @@ namespace OpenSim.Region.Framework.Scenes | |||
412 | /// asynchronously from the update loop. | 429 | /// asynchronously from the update loop. |
413 | /// </summary> | 430 | /// </summary> |
414 | private bool m_cleaningTemps = false; | 431 | private bool m_cleaningTemps = false; |
415 | 432 | ||
416 | // private Object m_heartbeatLock = new Object(); | 433 | /// <summary> |
434 | /// Used to control main scene thread looping time when not updating via timer. | ||
435 | /// </summary> | ||
436 | private ManualResetEvent m_updateWaitEvent = new ManualResetEvent(false); | ||
417 | 437 | ||
418 | // TODO: Possibly stop other classes being able to manipulate this directly. | 438 | // TODO: Possibly stop other classes being able to manipulate this directly. |
419 | private SceneGraph m_sceneGraph; | 439 | private SceneGraph m_sceneGraph; |
@@ -782,7 +802,6 @@ namespace OpenSim.Region.Framework.Scenes | |||
782 | : this(regInfo, physicsScene) | 802 | : this(regInfo, physicsScene) |
783 | { | 803 | { |
784 | m_config = config; | 804 | m_config = config; |
785 | MinFrameTime = 0.089f; | ||
786 | MinMaintenanceTime = 1; | 805 | MinMaintenanceTime = 1; |
787 | SeeIntoRegion = true; | 806 | SeeIntoRegion = true; |
788 | 807 | ||
@@ -1005,7 +1024,11 @@ namespace OpenSim.Region.Framework.Scenes | |||
1005 | } | 1024 | } |
1006 | } | 1025 | } |
1007 | 1026 | ||
1008 | MinFrameTime = startupConfig.GetFloat( "MinFrameTime", MinFrameTime); | 1027 | if (startupConfig.Contains("MinFrameTime")) |
1028 | MinFrameTicks = (int)(startupConfig.GetFloat("MinFrameTime") * 1000); | ||
1029 | else | ||
1030 | MinFrameTicks = 89; | ||
1031 | |||
1009 | m_update_backup = startupConfig.GetInt( "UpdateStorageEveryNFrames", m_update_backup); | 1032 | m_update_backup = startupConfig.GetInt( "UpdateStorageEveryNFrames", m_update_backup); |
1010 | m_update_coarse_locations = startupConfig.GetInt( "UpdateCoarseLocationsEveryNFrames", m_update_coarse_locations); | 1033 | m_update_coarse_locations = startupConfig.GetInt( "UpdateCoarseLocationsEveryNFrames", m_update_coarse_locations); |
1011 | m_update_entitymovement = startupConfig.GetInt( "UpdateEntityMovementEveryNFrames", m_update_entitymovement); | 1034 | m_update_entitymovement = startupConfig.GetInt( "UpdateEntityMovementEveryNFrames", m_update_entitymovement); |
@@ -1445,7 +1468,7 @@ namespace OpenSim.Region.Framework.Scenes | |||
1445 | 1468 | ||
1446 | if (UpdateOnTimer) | 1469 | if (UpdateOnTimer) |
1447 | { | 1470 | { |
1448 | m_sceneUpdateTimer = new Timer(MinFrameTime * 1000); | 1471 | m_sceneUpdateTimer = new Timer(MinFrameTicks); |
1449 | m_sceneUpdateTimer.AutoReset = true; | 1472 | m_sceneUpdateTimer.AutoReset = true; |
1450 | m_sceneUpdateTimer.Elapsed += Update; | 1473 | m_sceneUpdateTimer.Elapsed += Update; |
1451 | m_sceneUpdateTimer.Start(); | 1474 | m_sceneUpdateTimer.Start(); |
@@ -1552,7 +1575,7 @@ namespace OpenSim.Region.Framework.Scenes | |||
1552 | runtc = (int)(MinMaintenanceTime * 1000) - runtc; | 1575 | runtc = (int)(MinMaintenanceTime * 1000) - runtc; |
1553 | 1576 | ||
1554 | if (runtc > 0) | 1577 | if (runtc > 0) |
1555 | Thread.Sleep(runtc); | 1578 | Thread.Sleep(runtc); |
1556 | 1579 | ||
1557 | // Optionally warn if a frame takes double the amount of time that it should. | 1580 | // Optionally warn if a frame takes double the amount of time that it should. |
1558 | if (DebugUpdates | 1581 | if (DebugUpdates |
@@ -1613,7 +1636,7 @@ namespace OpenSim.Region.Framework.Scenes | |||
1613 | if (Frame % m_update_physics == 0) | 1636 | if (Frame % m_update_physics == 0) |
1614 | { | 1637 | { |
1615 | if (PhysicsEnabled) | 1638 | if (PhysicsEnabled) |
1616 | physicsFPS = m_sceneGraph.UpdatePhysics(MinFrameTime); | 1639 | physicsFPS = m_sceneGraph.UpdatePhysics(MinFrameSeconds); |
1617 | 1640 | ||
1618 | if (SynchronizeScene != null) | 1641 | if (SynchronizeScene != null) |
1619 | SynchronizeScene(this); | 1642 | SynchronizeScene(this); |
@@ -1711,18 +1734,16 @@ namespace OpenSim.Region.Framework.Scenes | |||
1711 | { | 1734 | { |
1712 | Watchdog.UpdateThread(); | 1735 | Watchdog.UpdateThread(); |
1713 | 1736 | ||
1714 | tmpMS = Util.EnvironmentTickCountSubtract(Util.EnvironmentTickCount(), m_lastFrameTick); | 1737 | spareMS = MinFrameTicks - Util.EnvironmentTickCountSubtract(m_lastFrameTick); |
1715 | tmpMS = (int)(MinFrameTime * 1000) - tmpMS; | ||
1716 | 1738 | ||
1717 | if (tmpMS > 0) | 1739 | if (spareMS > 0) |
1718 | { | 1740 | m_updateWaitEvent.WaitOne(spareMS); |
1719 | spareMS = tmpMS; | 1741 | else |
1720 | Thread.Sleep(tmpMS); | 1742 | spareMS = 0; |
1721 | } | ||
1722 | } | 1743 | } |
1723 | else | 1744 | else |
1724 | { | 1745 | { |
1725 | spareMS = Math.Max(0, (int)(MinFrameTime * 1000) - physicsMS2 - agentMS - physicsMS -otherMS); | 1746 | spareMS = Math.Max(0, MinFrameTicks - physicsMS2 - agentMS - physicsMS - otherMS); |
1726 | } | 1747 | } |
1727 | 1748 | ||
1728 | previousFrameTick = m_lastFrameTick; | 1749 | previousFrameTick = m_lastFrameTick; |
@@ -1745,11 +1766,11 @@ namespace OpenSim.Region.Framework.Scenes | |||
1745 | // Optionally warn if a frame takes double the amount of time that it should. | 1766 | // Optionally warn if a frame takes double the amount of time that it should. |
1746 | if (DebugUpdates | 1767 | if (DebugUpdates |
1747 | && Util.EnvironmentTickCountSubtract( | 1768 | && Util.EnvironmentTickCountSubtract( |
1748 | m_lastFrameTick, previousFrameTick) > (int)(MinFrameTime * 1000 * 2)) | 1769 | m_lastFrameTick, previousFrameTick) > MinFrameTicks * 2) |
1749 | m_log.WarnFormat( | 1770 | m_log.WarnFormat( |
1750 | "[SCENE]: Frame took {0} ms (desired max {1} ms) in {2}", | 1771 | "[SCENE]: Frame took {0} ms (desired max {1} ms) in {2}", |
1751 | Util.EnvironmentTickCountSubtract(m_lastFrameTick, previousFrameTick), | 1772 | Util.EnvironmentTickCountSubtract(m_lastFrameTick, previousFrameTick), |
1752 | MinFrameTime * 1000, | 1773 | MinFrameTicks, |
1753 | RegionInfo.RegionName); | 1774 | RegionInfo.RegionName); |
1754 | } | 1775 | } |
1755 | 1776 | ||
diff --git a/OpenSim/Region/Framework/Scenes/SimStatsReporter.cs b/OpenSim/Region/Framework/Scenes/SimStatsReporter.cs index 95f9caf..8f1e345 100644 --- a/OpenSim/Region/Framework/Scenes/SimStatsReporter.cs +++ b/OpenSim/Region/Framework/Scenes/SimStatsReporter.cs | |||
@@ -224,7 +224,7 @@ namespace OpenSim.Region.Framework.Scenes | |||
224 | public SimStatsReporter(Scene scene) | 224 | public SimStatsReporter(Scene scene) |
225 | { | 225 | { |
226 | m_scene = scene; | 226 | m_scene = scene; |
227 | m_reportedFpsCorrectionFactor = scene.MinFrameTime * m_nominalReportedFps; | 227 | m_reportedFpsCorrectionFactor = scene.MinFrameSeconds * m_nominalReportedFps; |
228 | m_statsUpdateFactor = (float)(m_statsUpdatesEveryMS / 1000); | 228 | m_statsUpdateFactor = (float)(m_statsUpdatesEveryMS / 1000); |
229 | ReportingRegion = scene.RegionInfo; | 229 | ReportingRegion = scene.RegionInfo; |
230 | 230 | ||
@@ -239,7 +239,7 @@ namespace OpenSim.Region.Framework.Scenes | |||
239 | 239 | ||
240 | /// At the moment, we'll only report if a frame is over 120% of target, since commonly frames are a bit | 240 | /// At the moment, we'll only report if a frame is over 120% of target, since commonly frames are a bit |
241 | /// longer than ideal (which in itself is a concern). | 241 | /// longer than ideal (which in itself is a concern). |
242 | SlowFramesStatReportThreshold = (int)Math.Ceiling(m_scene.MinFrameTime * 1000 * 1.2); | 242 | SlowFramesStatReportThreshold = (int)Math.Ceiling(scene.MinFrameTicks * 1.2); |
243 | 243 | ||
244 | SlowFramesStat | 244 | SlowFramesStat |
245 | = new Stat( | 245 | = new Stat( |